Component slots
Replace the built-in components with custom implementation
month-year
Create and use a custom component implementation in the header for month/year select
Info
When using this slot, the overlays will not be available, it is up to you to create them if you want
This slot exposes the following:
month
(number
)- Selected month value
year
(number
)- Selected year value
months
({ text: string; value: number }[]
)- Generated array of months
years
({ text: string; value: number }[]
)- Generated array of years
updateMonthYear
((month: number, year: number) => void
)- Exposed function to update month and year
handleMonthYearChange
((isNext: boolean) => void
)- Exposed function to auto handle next/previous month
instance
(number
)- In case of multi-calendars, instance is the order of the calendar
Code Example
vue
<template>
<VueDatePicker v-model="date">
<template
#month-year="{
month,
year,
months,
years,
updateMonthYear,
handleMonthYearChange
}">
<div class="custom-month-year-component">
<select
class="select-input"
:value="month"
@change="updateMonth($event, updateMonthYear, year)">
<option v-for="m in months" :key="m.value" :value="m.value">{{ m.text }}</option>
</select>
<select
class="select-input"
:value="year"
@change="updateYear($event, updateMonthYear, month)">
<option v-for="y in years" :key="y.value" :value="y.value">{{ y.text }}</option>
</select>
</div>
<div class="icons">
<span
class="custom-icon"
@click="handleMonthYearChange(false)">
<ChevronLeftIcon />
</span>
<span
class="custom-icon"
@click="handleMonthYearChange(true)">
<ChevronRightIcon />
</span>
</div>
</template>
</VueDatePicker>
</template>
<script lang="ts" setup>
import { ref } from 'vue';
import ChevronLeftIcon from './Icons/ChevronLeftIcon.vue';
import ChevronRightIcon from './Icons/ChevronRightIcon.vue';
const date = ref(new Date());
type UpdateMonthYear = (month: number, year: number) => void;
const updateMonth = (event: InputEvent, updateMonthYear: UpdateMonthYear, year: number) => {
updateMonthYear(+(event.target as HTMLSelectElement).value, year);
};
const updateYear = (event: InputEvent, updateMonthYear: UpdateMonthYear, month: number) => {
updateMonthYear(month, +(event.target as HTMLSelectElement).value);
};
</script>
<style lang="scss">
.custom-month-year-component {
display: flex;
align-items: center;
margin: 0 auto;
}
.select-input {
margin: 5px 3px;
padding: 5px;
width: auto;
border-radius: 4px;
border-color: var(--dp-border-color);
outline: none;
-webkit-appearance: menulist;
}
.icons {
display: flex;
box-sizing: border-box;
}
.custom-icon {
padding: 5px;
display: flex;
height: 25px;
align-items: center;
justify-content: center;
cursor: pointer;
width: 25px;
color: var(--dp-icon-color);
text-align: center;
border-radius: 50%;
svg {
height: 20px;
width: 20px;
}
&:hover {
background: var(--dp-hover-color);
}
}
</style>
time-picker
Create and use a custom component for the time picker
This slot exposes the following:
time
(Time
)- Reactive time object with hours, minutes and seconds
updateTime
(UpdateTime
)- Exposed function to update time
ts
// Array values are used if range is enabled
interface Time {
hours: number | number[];
minutes: number | number[];
seconds: number | number[]
}
type UpdateTime = (value: number | number[], isHours: boolean, isSeconds: boolean) => void;
Info
Keep in mind that when you are using the range picker, both values for the time must be emitted. For example if you want to update the second date hours, you will call a function something like this updateTime([firstValueSaved, newSecondValue])
Code Example
vue
<template>
<VueDatePicker v-model="date">
<template #time-picker="{ time, updateTime }">
<div class="custom-time-picker-component">
<select
class="select-input"
:value="time.hours"
@change="updateTime(+$event.target.value)"
>
<option
v-for="h in hoursArray"
:key="h.value"
:value="h.value">{{ h.text }}</option>
</select>
<select
class="select-input"
:value="time.minutes"
@change="updateTime(+$event.target.value, false)"
>
<option
v-for="m in minutesArray"
:key="m.value"
:value="m.value">{{ m.text }}</option>
</select>
</div>
</template>
</VueDatePicker>
</template>
<script lang="ts" setup>
import { ref, computed } from 'vue';
const date = ref(new Date());
const hoursArray = computed(() => {
const arr = [];
for (let i = 0; i < 24; i++) {
arr.push({ text: i < 10 ? `0${i}` : i, value: i });
}
return arr;
});
const minutesArray = computed(() => {
const arr = [];
for (let i = 0; i < 60; i++) {
arr.push({ text: i < 10 ? `0${i}` : i, value: i });
}
return arr;
});
</script>
<style lang="scss">
.custom-time-picker-component {
display: flex;
align-items: center;
justify-content: center;
}
.select-input {
margin: 5px 3px;
padding: 5px;
width: 100px;
border-radius: 4px;
border-color: var(--dp-border-color);
outline: none;
-webkit-appearance: menulist;
}
</style>
action-row
Create and use a custom component for action row
This slot exposes the following:
internalModelValue
(Date | Date[] | null
)- Current selected value in the datepicker
selectDate
(() => void
)- Select the current
internalModelValue
value
- Select the current
closePicker
(() = void
)- Close the datepicker menu
disabled
(boolean
)- If the value is invalid based on the provided configuration
Code Example
vue
<template>
<VueDatePicker v-model="date">
<template #action-row="{ internalModelValue, selectDate }">
<div class="action-row">
<p class="current-selection">{{ formatDate(internalModelValue) }}</p>
<button class="select-button" @click="selectDate">Select Date</button>
</div>
</template>
</VueDatePicker>
</template>
<script lang="ts" setup>
import { ref } from 'vue';
import { format } from 'date-fns'
const date = ref(new Date());
const formatDate = (date: Date) => {
return format(date, 'dd.MM.yyyy, HH:mm');
};
</script>
<style lang="scss">
.action-row {
display: flex;
flex-direction: column;
align-items: center;
width: 100%;
}
</style>