1. 程式人生 > >使用Vux的Datetime以及XNumber元件實現日期聯動

使用Vux的Datetime以及XNumber元件實現日期聯動

實現效果

知識儲備

XNumber元件

安裝

區域性註冊:

import { XNumber } from 'vux'

export default {
  components: {
    XNumber
  }
}

全域性註冊:

// 在入口檔案全域性引入

import Vue from 'vue'
import { XNumber } from 'vux'

Vue.component('x-number', XNumber)

使用

注:x-number只能在Group中使用

 <group>
    <x-number title="title" v-model="value"></x-number>
  </group>

屬性

名字 型別 預設值 說明 版本要求
value number 0 表單值,使用v-model繫結 --
title string   標題 --
min number   最小值 --
max number   最大值 --
step number 1 步長 --
fillable boolean false 是否可填寫 --
width string 50px 輸入框寬度 --
button-style string square 按鈕樣式,可選值為square或者round --
align string right 按鈕部分位置,預設在右邊(right),可選值為leftright --

   

樣式變數

 

名字 預設值 說明 繼承自變數
@number-button-font-color #3cc51f --  
@number-input-font-color  #666 --  
@number-button-enabled-border-color #ececec --  
@number-square-button-enabled-border-color #ececec -- @number-button-enabled-border-color
@number-round-button-enabled-border-color #3cc51f -- @number-button-font-color
@number-button-disabled-border-color #ececec -- @number-button-enabled-border-color
@number-round-button-disabled-border-color #ececec -- @number-button-enabled-border-color


Demo原始碼

<template>
  <div>
    <group :title="$t('Default')">
      <x-number :name="$t('Quantity')" :title="$t('Quantity')"></x-number>
    </group>

    <group :title="$t('listen')">
      <x-number :title="$t('Quantity')" v-model="changeValue" :min="0" @on-change="change"></x-number>
    </group>

    <group :title="$t('set width=100px')">
      <x-number :title="$t('Quantity')" width="100px"></x-number>
    </group>

    <group :title="$t('round style')">
      <x-number :title="$t('Quantity')" v-model="roundValue" button-style="round" :min="0" :max="5"></x-number>
    </group>

    <group :title="$t('set step=0.5')">
      <x-number :title="$t('Quantity')" :step="0.5"></x-number>
    </group>

    <group :title="$t('set value=1, min=-5 and max=8')">
      <x-number :title="$t('Quantity')" :min="-5" :max="8" :value="1"></x-number>
    </group>

    <group :title="$t('fillable = true')">
      <x-number :value="10" :title="$t('Quantity')" fillable></x-number>
    </group>

  </div>
</template>

<i18n>
Default:
  zh-CN: 預設
Quantity:
  zh-CN: 數量
listen:
  en: listen to on-change events (printed on console)
  zh-CN: 監聽 on-change 事件,在除錯視窗中輸出
set width=100px:
  zh-CN: 設定寬度為100px
set step=0.5:
  zh-CN: 設定步長為0.5
set value=1, min=-5 and max=8:
  zh-CN: 設定值為1,最小值為-5,最大值為8
fillable = true:
  zh-CN: 設定可以輸入
use with other group elements:
  zh-CN: 和其他group子元素一起使用
Switch Component:
  zh-CN: Switch 元件
round style:
  zh-CN: 圓形按鈕
</i18n>

<script>
import { Group, XNumber, XSwitch, Divider } from 'vux'

export default {
  components: {
    XNumber,
    Group,
    XSwitch,
    Divider
  },
  data () {
    return {
      changeValue: 0,
      roundValue: 0
    }
  },
  methods: {
    change (val) {
      console.log('change', val)
    }
  }
}
</script>

Datetime元件

安裝

區域性註冊:

import { Datetime } from 'vux'

export default {
  components: {
    Datetime
  }
}

全域性註冊:

// 在入口檔案全域性引入

import Vue from 'vue'
import { Datetime } from 'vux'

Vue.component('datetime', Datetime)

使用

需要在Group元件內使用

該元件支援以Plugin形式呼叫

// 以 plugin 形式使用時,請在入口處引入:
import { DatetimePlugin } from 'vux'
Vue.use(DatetimePlugin)

// 元件內使用
this.$vux.datetime.show({
  value: '', // 其他引數同 props
  onHide () {
    const _this = this
  },
  onShow () {
    const _this = this
  }
})

this.$vux.datetime.hide()

屬性

參考官方文件:

https://doc.vux.li/zh-CN/components/datetime.html

事件

 

名字 引數 說明 版本要求
@on-change (value) 表單值變化時觸發, 引數 (newVal) --
@on-clear -- 點選顯示在中間的自定義按鈕時觸發 --
@on-show -- 彈窗顯示時觸發 --
@on-hide (type), type is one of [cancel, confirm] 彈窗關閉時觸發 v2.7.4
@on-cancel -- 點選取消按鈕或者遮罩時觸發,等同於事件 on-hide(cancel) v2.7.4
@on-confirm (value) v2.9.0 支援該引數 點選確定按鈕時觸發,等同於事件 on-hide(confirm) v2.7.4

Demo原始碼

<template>
  <div>
    <div style="padding:15px;">
      <x-button type="primary" plain @click.native="showPlugin">{{ $t('Used as a plugin') }}</x-button>
    </div>

    <group :title="$t('Default format: YYYY-MM-DD')">
      <datetime
        v-model="value1"
        @on-change="change"
        :title="$t('Birthday')"
        @on-cancel="log('cancel')"
        @on-confirm="onConfirm"
        @on-hide="log('hide', $event)"></datetime>
    </group>

    <group :title="$t('Custom minute list: every 15 minutes')">
      <datetime v-model="minuteListValue" format="YYYY-MM-DD HH:mm" :minute-list="['00', '15', '30', '45']" @on-change="change" :title="$t('Birthday')"></datetime>
    </group>

    <group :title="$t('Custom hour list')">
      <datetime v-model="hourListValue" format="YYYY-MM-DD HH:mm" :hour-list="['09', '10', '11', '12', '13', '14', '15', '16']" :minute-list="['00', '15', '30', '45']" @on-change="change" :title="$t('Birthday')"></datetime>
    </group>

    <group title="Readonly">
      <datetime v-model="valueReadonly" :readonly="readonly" @on-change="change" :title="$t('Birthday')"></datetime>
    </group>
    <div style="padding:15px">
      <x-button type="primary" plain @click.native="readonly = !readonly"> {{ $t('Toggle readonly') }} </x-button>
    </div>

     <group :title="$t('Format display value')">
      <datetime v-model="formatValue" :display-format="formatValueFunction" @on-change="change" :title="$t('Birthday')"></datetime>
    </group>

    <div style="padding:15px;">
      <x-button type="primary" @click.native="formatValue = '2017-11-11'">{{ $t('Set value: 2017-11-11') }}</x-button>
    </div>

    <group :title="$t('Define range of hours')">
      <datetime v-model="limitHourValue" format="YYYY-MM-DD HH:mm" :min-hour=9 :max-hour=18 @on-change="change" :title="$t('Define range of hours')" :inline-desc="$t('Working hours: 09-18')"></datetime>
    </group>

    <group :title="$t('Set start-date and end-date') + ' 2015-11-11 ~ 2017-10-11'">
      <datetime v-model="limitHourValue" :start-date="startDate" :end-date="endDate" format="YYYY-MM-DD HH:mm" @on-change="change" :title="$t('Start time')"></datetime>
    </group>

     <group :title="$t('Set end-date only') + ' 2017-10-11'">
      <datetime v-model="onlySetEndDateValue" :end-date="onlySetEndDate" format="YYYY-MM-DD HH:mm" @on-change="change" :title="$t('Start time')"></datetime>
    </group>

    <group :title="$t('Format') + ': ' + format">
      <datetime v-model="value2" :format="format" @on-change="change" :title="$t('Start time')"></datetime>
    </group>

    <div style="padding:15px;">
      <x-button type="primary" @click.native="toggleFormat">{{ $t('Toggle format') }}</x-button>
    </div>

    <group title="noon">
      <datetime title="noon" v-model="noonValue" format="YYYY-MM-DD A"></datetime>
    </group>

    <group :title="$t('Placeholder')">
      <datetime v-model="value3" default-selected-value="2017-06-18 13" format="YYYY-MM-DD HH" :placeholder="$t('Please select')" @on-change="change" :title="$t('Start time')"></datetime>
    </group>

    <group :title="$t('Set default-selected-value to 2017-11-11')">
      <datetime v-model="value3_1" default-selected-value="2017-11-11" format="YYYY-MM-DD" :placeholder="$t('Please select')" @on-change="change" :title="$t('Start time')" :inline-desc=" $t('Current value') + `: ${value3_1}`"></datetime>
    </group>

    <group :title="$t('Set min-year and max-year')">
      <datetime v-model="value4" :placeholder="$t('Please select')" :min-year=2000 :max-year=2016 format="YYYY-MM-DD HH:mm" @on-change="change" :title="$t('Years after 2000')"></datetime>
    </group>

    <group :title="$t('Prop: compute-hours-function')">
      <datetime format="YYYY-MM-DD HH" v-model="computeHoursValue" :compute-hours-function="computeHoursFunction" :title="$t('Birthday')" @on-change="change"></datetime>
    </group>

    <group :title="$t('Prop: compute-days-function')">
      <datetime format="YYYY-MM-DD HH" v-model="computeDaysValue" :compute-days-function="computeDaysFunction" :title="$t('Birthday')" @on-change="change"></datetime>
    </group>

    <group :title="$t('Specified template text in Chinese')">
      <datetime v-model="value5" :placeholder="$t('Please select')" :min-year=2000 :max-year=2016 format="YYYY-MM-DD HH:mm" @on-change="change" :title="$t('Chinese')" year-row="{value}年" month-row="{value}月" day-row="{value}日" hour-row="{value}點" minute-row="{value}分" confirm-text="完成" cancel-text="取消"></datetime>
    </group>

    <group :title="$t('Show center button and clear the value')">
      <datetime v-model="value6" @on-change="change" :title="$t('Birthday')" clear-text="clear" @on-clear="clearValue"></datetime>
    </group>

    <group :title="$t('Show center button to set date to today')">
      <datetime v-model="value7" @on-change="change" :title="$t('Birthday')" clear-text="today" @on-clear="setToday"></datetime>
    </group>

     <group :title="$t('Custom trigger slot')">
      <datetime v-model="value7" @on-change="change" :title="$t('Birthday')" clear-text="today" @on-clear="setToday">
        <x-button>{{$t('Click me')}}</x-button>
      </datetime>
    </group>

    <group :title="$t('Required')">
      <datetime v-model="value8" :title="$t('Required')" clear-text="clear" @on-clear="clearValue8" :required="true"></datetime>
    </group>

    <group :title="$t('Use prop: show.sync (vue^2.3) to control visibility')">
      <datetime v-model="value9" @on-change="change" :title="$t('Birthday')" :show.sync="visibility"></datetime>
    </group>

    <div style="padding:15px;">
      <x-button type="primary" plain @click.native="visibility = true">顯示</x-button>
    </div>

    <group :title="$t('Default format: YYYY-MM-DD')">
      <datetime
        :order-map="{
          year: 3,
          month: 2,
          day: 1
        }"
        v-model="value1"
        @on-change="change"
        title="customize column order"
        @on-cancel="log('cancel')"
        @on-confirm="onConfirm"
        @on-hide="log('hide', $event)"></datetime>
    </group>


  </div>
</template>

<i18n>
'Default format: YYYY-MM-DD':
  zh-CN: 預設格式:YYYY-MM-DD
Format:
  zh-CN: 格式
Start time:
  zh-CN: 開始時間
Placeholder:
  zh-CN: 提示文字
Please select:
  zh-CN: 請選擇
Set min-year and max-year:
  zh-CN: 設定開始和結束年份
Years after 2000:
  zh-CN: 2000年以後的時間
Specified template text in Chinese:
  zh-CN: 自定義中文顯示模板
Show center button and clear the value:
  zh-CN: 顯示中間的清除按鈕
Show center button to set date to today:
  zh-CN: 顯示中間的設定日期為今天的按鈕
Birthday:
  zh-CN: 生日
Chinese:
  zh-CN: 中文
Click me:
  zh-CN: 點我
Custom trigger slot:
  zh-CN: 自定義觸發內容
Define range of hours:
  zh-CN: 限定小時範圍
'Working hours: 09-18':
  zh-CN: 工作時間為 09-18
Set start-date and end-date:
  zh-CN: 設定開始時間和結束日期
'Click to change value to: 2017-11-11':
  zh-CN: 設定時間為 2017-11-11
Format display value:
  zh-CN: 格式化顯示
Toggle format:
  zh-CN: 改變格式
'Custom minute list: every 15 minutes':
  zh-CN: 自定義分鐘列表(每15分鐘)
Custom hour list:
  zh-CN: 定義小時列表
'Use prop: show.sync (vue^2.3) to control visibility':
  zh-CN: '使用 prop: show.sync 控制顯示(vue^2.3)'
Used as a plugin:
  zh-CN: 外掛形式呼叫
Set default-selected-value to 2017-11-11:
  zh-CN: 設定預設選中值為 2017-11-11
'Prop: compute-hours-function':
  zh-CN: 自定義小時列表生成邏輯
'Prop: compute-days-function':
  zh-CN: 自定義日期列表生成邏輯
Toggle readonly:
  zh-CN: 切換 readonly 屬性
'Set value: 2017-11-11':
  zh-CN: 設定時間為2017-11-11
Set end-date only:
  zh-CN: 只設置結束時間
</i18n>

<script>
import { Datetime, Group, XButton } from 'vux'

export default {
  components: {
    Datetime,
    Group,
    XButton
  },
  data () {
    return {
      noonValue: '2018-04-13 PM',
      readonly: true,
      minuteListValue: '2017-06-12 09:00',
      hourListValue: '2017-06-12 09:00',
      format: 'YYYY-MM-DD HH:mm',
      value1: '2015-11-12',
      valueReadonly: '2015-11-12',
      value2: '',
      value3: '',
      value3_1: '',
      value4: '',
      value5: '',
      value6: '2016-08-18',
      value7: '',
      value8: '',
      limitHourValue: '',
      startDate: '2015-11-11',
      endDate: '2017-10-11',
      formatValue: '2017-10-11',
      formatValueFunction (val) {
        return val.replace(/-/g, '$')
      },
      value9: '',
      visibility: false,
      computeHoursValue: '',
      computeDaysValue: '',
      computeHoursFunction (date, isToday, generateRange) {
        if (isToday) {
          return generateRange(new Date().getHours(), 23)
        } else {
          return generateRange(0, 23)
        }
      },
      computeDaysFunction (options, generateRange) {
        return [options.month] // if current month is n, days are [n]
      },
      onlySetEndDate: '2017-10-11',
      onlySetEndDateValue: ''
    }
  },
  methods: {
    log (str1, str2 = '') {
      console.log(str1, str2)
    },
    onConfirm (val) {
      console.log('on-confirm arg', val)
      console.log('current value', this.value1)
    },
    showPlugin () {
      this.$vux.datetime.show({
        cancelText: '取消',
        confirmText: '確定',
        format: 'YYYY-MM-DD HH',
        value: '2017-05-20 18',
        onConfirm (val) {
          console.log('plugin confirm', val)
        },
        onShow () {
          console.log('plugin show')
        },
        onHide () {
          console.log('plugin hide')
        }
      })
    },
    toggleFormat () {
      if (this.format === 'YYYY-MM-DD') {
        this.format = 'YYYY-MM-DD HH:mm'
      } else if (this.format === 'YYYY-MM-DD HH:mm') {
        this.format = 'YYYY-MM-DD'
      }
    },
    change (value) {
      console.log('change', value)
    },
    clearValue (value) {
      this.value6 = ''
    },
    clearValue8 (value) {
      this.value8 = ''
    },
    setToday (value) {
      let now = new Date()
      let cmonth = now.getMonth() + 1
      let day = now.getDate()
      if (cmonth < 10) cmonth = '0' + cmonth
      if (day < 10) day = '0' + day
      this.value7 = now.getFullYear() + '-' + cmonth + '-' + day
      console.log('set today ok')
    }
  }
}
</script>

<style scoped lang="less">
.center {
  padding-top: 10px;
  padding-left: 15px;
  color: green;
}
</style>

實現日期聯動

在vue單頁面中 

 <group class="mt_cd_0">

          <x-number class= " h_36em pb_0 pt_0"v-if="demandForm.flightTypeArray==2" title="出行天數" width="50px" :min="1"
           @on-change="changeReturnDate"
           v-model="demandForm.tripDays"></x-number>
  </group>

注:

v-if:業務需求,當為2時才顯示這個控制元件

title:要顯示的標題

width:寬度

:min:最小值為1,不能再往下減

@on-change:發生改變時執行的方法

 v-model:繫結的v-model的值

然後在data中宣告:

 

 data() {
      return {   
        demandForm: {
          tripDays: 1,    
          goStartTime: '',
          goEndTime: '',
          returnStartTime: '',
          returnEndTime: '',
          demandCloseTime: '',
        }
      }
}

當x-number的值發生改變時,會執行changeReturnDate方法,所以在此方法中:

methods: {
      changeReturnDate(){
       if(this.demandForm.tripDays!=''&&this.demandForm.goStartTime!=''){
          var goStartTime=new Date(this.demandForm.goStartTime)
          var returnStartTime=new Date(this.demandForm.returnStartTime)
          returnStartTime=new Date(goStartTime.getTime() +this.demandForm.tripDays * 24 * 60 * 60 * 1000);
          this.demandForm.returnStartTime=dateFormat(returnStartTime, 'YYYY-MM-DD').toString();
        }
       if(this.demandForm.tripDays!=''&&this.demandForm.goEndTime!=''){
          var goEndTime=new Date(this.demandForm.goEndTime)
          var returnEndTime=new Date(this.demandForm.returnEndTime)
          returnEndTime=new Date(goEndTime.getTime()+this.demandForm.tripDays* 24 * 60 * 60 * 1000);
          this.demandForm.returnEndTime=dateFormat(returnEndTime, 'YYYY-MM-DD').toString();
        }
      },

注:

if(出行天數不為空&&去程開始時間不為空){

獲取去程開始時間並轉化為Date格式;

獲取返程開始時間並轉化為Date格式;

返程開始時間=轉化為Date(去程開始時間的毫秒基數+去程天數的毫秒數);

返程開始時間=按指定格式格式化後的時間並轉換為String格式;

}

下面返程結束時間同理。

注意:

使用JS 獲取去程開始時間n天后的時間:

 var nTime=new Date(goStartTime.getTime() +n* 24 * 60 * 60 * 1000);