android 仿飞猪日历,vue 日期选择 类似飞猪

实现功能

基本照抄ixc-page-calendar日历, 没有配置头部, 单一动画可自己扩展

注意返回的iconFont可以自己的

3917e593270c?utm_campaign=maleskine&utm_content=note&utm_medium=seo_notes&utm_source=recommendation

GkA9rgFNsS.gif

vue文件

选择日期

:key="k"

:aria-label="`周${week}`"

v-for="(week,k) in ['日','一','二','三','四','五','六']">{{week}}

:key="index"

:id="sub+month.title"

:class="[!month.title && 'calendar-row']">

v-if="month.title">{{month.title}}

v-for="(cell,rowIndex) in month"

:key="`${index}-${rowIndex}`"

:ref="cell.ref"

:class="['row-item', cell.cellClass]"

:style="cell.isSelected ? selectedCellStyle:{}"

:accessible="true"

:aria-label="`${cell.text?cell.text:''},${cell.note?cell.note:''},${cell.ext?cell.ext:''}`"

@click="onClickDate(cell)">

:style="cell.isSelected ? selectedTextStyle:{}">{{cell.note}}

:style="cell.isSelected ? selectedTextStyle:{}">{{cell.text}}

:style="cell.isSelected ? selectedTextStyle:{}">{{cell.ext}}

import Format from './format.js'

export default {

components: {},

props: {

selectedDate: Array,

dateRange: {

type: Array,

required: true,

default: () => ([])

},

selectedNote: {

type: Array,

default: () => (['开始', '到达', '往返'])

},

isRange: {

type: Boolean,

default: false

},

needDestroy: {

type: Boolean,

default: false

},

descList: {

type: Array,

default: () => ([])

},

selectedCellStyle: {

type: Object,

default: () => ({})

},

selectedTextStyle: {

type: Object,

default: () => ({})

},

},

computed: {

today(){

return Format.getToDay()

},

monthsArray () {

const { dateRange: range, today, departDate, arriveDate, selectedNote, descList } = this;

const param = { range, today, departDate, arriveDate, selectedNote, descList }

return Format.generateDateCell(param);

}

},

data: () => ({

Format: Format,

showPage: false,

reSelect: true,

scrollIntoId: '',

departDate: '',

arriveDate: '',

sub: 'sub',

}),

created() {

},

mounted() {

},

methods: {

show(){

this.reSelect = true;

this.showPage = true;

this.detectShow();

},

back(){

this.reSelect = false;

this.showPage = false;

},

onClickDate (datConfig) {

const self = this;

if (datConfig.disabled || datConfig.isEmpty) return;

if (self.reSelect) {

self.departDate = '';

self.arriveDate = '';

self.reSelect = false;

}

if (self.isRange) {

if (self.departDate && Date.parse(self.departDate) <= Date.parse(datConfig.date)) {

self.arriveDate = datConfig.date;

} else {

self.departDate = datConfig.date;

}

if (self.departDate && self.arriveDate) {

self.dispatchDateChange([self.departDate, self.arriveDate]);

}

} else {

self.departDate = datConfig.date;

self.dispatchDateChange([self.departDate]);

}

},

dispatchDateChange (dateArr) {

const duration = 400;

setTimeout(() => {

this.back();

}, duration);

this.$emit('wxcPageCalendarDateSelected', {

date: dateArr

});

},

detectShow () {

if (this.isRange && this.selectedDate.length >= 2) {

this.departDate = this.selectedDate[0];

this.arriveDate = this.selectedDate[1];

} else if (this.selectedDate.length >= 1) {

this.departDate = this.selectedDate[0];

this.arriveDate = '';

}

for(var i = 0; i < this.monthsArray.length; i++){

var title = this.monthsArray[i].title

if(title){

var subtitle = this.sub+title

console.log('测试数据',title, this.departDate)

if(title == this.subId(this.departDate)){

this.scrollIntoId = this.sub + title

console.log('测试数据scrollIntoId',title, this.scrollIntoId)

}

}

}

},

subId(title){

return title.substring(0, 7)

},

}

};

@font-face {

font-family: 'iconfont';

src: url('~@/static/iconfont/iconfont.ttf');

}

.wrapper {

position: fixed;

z-index: 999999;

background: #ffffff;

height: 100%;

width: 100%;

top: 0px;

left: 0px;

}

.content {

height: 100%;

width: 100%;

background-color: #ffffff;

}

.show {

left: 0;

width: 100%;

transition: left .3s ease;

}

.hide {

left: 100%;

width: 100%;

transition: left .3s ease;

}

.header{

height: 83upx;

background-color: #00aafb;

display: flex;

flex-direction: row;

padding-top: 15upx;

padding-left: 15upx;

}

.icon-font{

font-family: 'iconfont';

font-size: 30upx;

}

.middle{

width: 100%;

display: flex;

padding-right: 95upx;

justify-content: center

}

.title{

font-size: 30upx;

color: white;

}

.calendar-weekday {

height: 60upx;

background-color: #ffffff;

border-bottom-width: 1upx;

border-top-width: 1upx;

border-color: #e2e2e2;

flex-direction: row;

display: flex;

border-bottom-style: solid;

justify-content: space-around;

align-items: center;

}

.flex-item {

flex: 1;

width: 20%;

text-align: center;

}

.weekday-text {

color: #000000;

flex: 1;

font-size: 24upx;

text-align: center;

}

.calendar-list {

position: absolute;

top: 143upx;

bottom: 0upx;

width: 100%;

}

.month-text {

font-size: 32upx;

height: 60upx;

line-height: 60upx;

width: 750upx;

display: flex;

text-align: center;

flex-direction: column;

align-items: center;

background-color: #f2f3f4;

}

.calendar-row {

height: 140upx;

display: flex;

flex-direction: row;

background-color: #ffffff;

border-bottom-width: 1px;

border-color: #f2f3f4;

border-bottom-style: solid;

align-items: center;

justify-content: space-between;

}

.row-item {

flex: 1;

height: 140upx;

padding-top: 10upx;

padding-bottom: 10upx;

display: flex;

flex-direction: column;

justify-content: center;

align-items: center;

}

.calendar-note {

height: 36upx;

line-height: 36upx;

font-size: 24upx;

color: #000000;

text-align: center;

}

.calendar-day {

height: 48upx;

line-height: 48upx;

font-size: 36upx;

color: #000000;

text-align: center;

}

.calendar-ext {

height: 36upx;

line-height: 36upx;

color: #999999;

text-align: center;

font-size: 24upx;

text-overflow: ellipsis;

}

.calendar-holiday {

color: #FF5000;

}

.calendar-rest {

color: #FF5000;

}

.item-row-selected {

color: #ffffff;

background-color: #FFC900;

text-align: center;

}

.item-text-selected {

color: #3d3d3d;

text-align: center;

}

.calendar-disabled {

color: #CCCCCC;

}

.cell-disabled {

background-color: #FBFBFB;

}

.calendar-day-include {

background-color: #FFF7D6;

}

Format.js文件

/**

* CopyRight (C) 2017-2022 Alibaba Group Holding Limited.

* Created by Tw93 on 2017/07/29.

*/

const Format = {

// 国际节日

GLOBAL_HOLIDAY: {

'01-01': '元旦',

'02-14': '情人',

'05-01': '劳动',

'06-01': '儿童',

'10-01': '国庆',

'12-25': '圣诞'

},

// 传统节日

TRADITIONAL_HOLIDAY: {

'除夕': ['2015-02-18', '2016-02-07', '2017-01-27', '2018-02-15', '2019-02-04', '2020-01-24'],

'春节': ['2015-02-19', '2016-02-08', '2017-01-28', '2018-02-16', '2019-02-05', '2020-01-25'],

'元宵': ['2015-03-05', '2016-02-22', '2017-02-11', '2018-03-02', '2019-02-19', '2020-02-08'],

'清明': ['2015-04-05', '2016-04-04', '2017-04-04', '2018-04-05', '2019-04-05', '2020-04-04'],

'端午': ['2015-06-20', '2016-06-09', '2017-05-30', '2018-06-18', '2019-06-07', '2020-06-25'],

'中秋': ['2015-09-27', '2016-09-15', '2017-10-04', '2018-09-24', '2019-09-13', '2020-10-01'],

'重阳': ['2015-10-21', '2016-10-09', '2017-10-28', '2018-10-17', '2019-10-07', '2020-10-25']

},

// 放假日

REST_DAYS: ['2017-10-01', '2017-10-02', '2017-10-03', '2017-10-04', '2017-10-05', '2017-10-06', '2017-10-07',

'2017-10-08'

],

// 工作日

WORK_DAYS: ['2017-09-30'],

_getTraditionalHoliday() {

const HOLIDAY_TEMP = {};

const keys = Object.keys(Format.TRADITIONAL_HOLIDAY);

keys.forEach((k) => {

const arr = Format.TRADITIONAL_HOLIDAY[k];

arr.forEach((i) => {

HOLIDAY_TEMP[i] = k;

})

});

return HOLIDAY_TEMP;

},

_isDate(obj) {

const type = obj === null ? String(obj) : {}.toString.call(obj) || 'object';

return type === '[object date]';

},

/**

* 检测Hash

*

* @method _checkHash

* @private

*/

_checkHash(url, hash) {

return url && url.match(/#/) && url.replace(/^.*#/, '') === hash;

},

/**

* 获取当前日期的毫秒数

* @method getTime

* @param {String} date

* @return {Number}

*/

getTime(date) {

if (Format._isDate(date)) {

return new Date(date).getTime();

} else {

try {

return new Date(date.replace(/-/g, '/')).getTime();

} catch (e) {

return 0;

}

}

},

_isInRange(range, date) {

const start = Format.getTime(range[0]);

const end = Format.getTime(range[1]);

const d = Format.getTime(date);

return (start <= d && end >= d);

},

_isInSelectRange(range, date) {

const start = Format.getTime(range[0]);

const end = Format.getTime(range[1]);

const d = Format.getTime(date);

return (start < d && end > d);

},

_fixNum(num) {

return (num < 10 ? '0' : '') + num;

},

/**

* 是否是周末

* @method isWeekend

* @param {String} date

* @return {Boolean}

*/

_isWeekend(date) {

const day = new Date(date.replace(/-/g, '/')).getDay();

return day === 0 || day === 6;

},

/**

* 是否是今天

* @method isToday

* @param {String} date

* @return {Boolean}

*/

_isToday(today, date) {

return Format.getTime(today) === Format.getTime(date);

},

/**

* 检查是否是闰年

* @method _checkLeapYear

* @param {Number} y 年份

* @param {Date} t today

* @protected

*/

_getMonthDays(y, t) {

const MONTH_DAYS = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];

const year = y || t.getFullYear();

let isLeapYear = false;

if (year % 100) {

isLeapYear = !(year % 4);

} else {

isLeapYear = !(year % 400);

}

if (isLeapYear) {

MONTH_DAYS[1] = 29;

} else {

MONTH_DAYS[1] = 28;

}

return MONTH_DAYS;

},

/**

* 当月1号前面有多少空格

* @method _getPadding

* @protected

*/

_getPadding(year, month) {

const date = new Date(year + '/' + month + '/1');

return date.getDay();

},

_unique(array) {

return Array.prototype.filter.call(array, function(item, index) {

return array.indexOf(item) === index;

});

},

getToDay() {

return new Date().getFullYear() + '-' + Format._fixNum(new Date().getMonth() + 1) + '-' + Format._fixNum(new Date().getDate());

},

getWeekRows(y, m, today, dateRange, departDate, arriveDate, selectedNote, descList) {

const monthDays = Format._getMonthDays(y, today);

const padding = Format._getPadding(y, m, 7);

const num = monthDays[m - 1] + padding;

const rows = Math.ceil(num / 7);

const remain = num % 7;

const rowsData = [];

for (let i = 1; i <= rows; i++) {

const cells = [];

for (let j = 1; j <= 7; j++) {

let cell = {};

// 前后空格

if (i === 1 && j <= padding || remain && i === rows && j > remain) {

cell.isEmpty = true;

} else {

const d = (i - 1) * 7 + j - padding;

const date = y + '-' + Format._fixNum(m) + '-' + Format._fixNum(d);

let cls = [];

let ref = '';

const cellClass = [];

const isInRange = Format._isInRange(dateRange, date);

let disabled = false;

const global = Format._fixNum(m) + '-' + Format._fixNum(d);

let note = '';

let ext = '';

let isSelected = false;

if (descList && descList.length > 0) {

const nowDesc = descList.filter(item => item.date === date);

if (nowDesc && nowDesc.length > 0) {

ext = nowDesc[0].value;

if (nowDesc[0].emphasize) {

cls.push('calendar-holiday');

}

}

}

// 国际节日

if (Format.GLOBAL_HOLIDAY[global]) {

note = Format.GLOBAL_HOLIDAY[global];

cls.push('calendar-holiday');

}

const tHoliday = Format._getTraditionalHoliday()[date];

// 传统节日

if (tHoliday) {

note = tHoliday;

cls.push('calendar-holiday');

}

// 放假日

if (Format.REST_DAYS.indexOf(date) > -1) {

cls.push('calendar-holiday');

}

// 工作日

if (Format.WORK_DAYS.indexOf(date) > -1) {

cls.push('calendar-work');

}

// 周末

if (Format._isWeekend(date)) {

cls.push('calendar-holiday');

}

// 今天

if (Format._isToday(today, date)) {

cls.push('calendar-today');

note = '今天';

}

// 不在日期范围内

if (!isInRange) {

disabled = true;

}

if (disabled) {

cls = [];

cls.push('calendar-disabled');

cellClass.push('cell-disabled');

}

if (!ext && disabled && isInRange) {

ext = '不可选';

}

if (departDate === date || arriveDate === date) {

note = departDate === date ? selectedNote[0] : selectedNote[1];

ref = departDate === date ? 'departDate' : 'arriveDate';

if (departDate === arriveDate && selectedNote.length >= 3) {

note = selectedNote[2];

}

isSelected = true;

cls.push('item-text-selected');

cellClass.push('item-row-selected');

}

if (departDate && arriveDate && Format._isInSelectRange([departDate, arriveDate], date)) {

cellClass.push('calendar-day-include');

}

cell = {

isSelected,

isEmpty: false,

ref,

cls: Format._unique(cls).join(' '),

cellClass: Format._unique(cellClass).join(' '),

note: note,

date: date,

ext: ext,

disabled: disabled,

text: d

};

}

cells.push(cell);

}

rowsData.push(cells);

}

return rowsData;

},

generateDateCell({

range,

today,

departDate,

arriveDate,

selectedNote,

descList

}) {

const start = new Date(range[0].replace(/-/g, '/'));

const end = new Date(range[1].replace(/-/g, '/'));

const startYear = start.getFullYear();

const startMonth = start.getMonth() + 1;

const endYear = end.getFullYear();

const endMonth = end.getMonth() + 1;

const l = (endYear - startYear) * 12 + endMonth - startMonth + 1;

let y = startYear;

let n = startMonth;

const months = [];

for (let i = 0; i < l; i++) {

if (n > 12) {

n = 1;

y++;

}

months.push({

title: `${y}-${Format._fixNum(n)}`

},

...Format.getWeekRows(y, n, today, range, departDate, arriveDate, selectedNote, descList)

);

n++;

}

return months

},

}

export default Format

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值