vuetify
vuetify copied to clipboard
Feat(VCalendar): Add eventHandlers and slots
<template>
<v-app>
<v-main>
<v-container>
<v-row>
<v-col>
<v-select v-model="view" :items="['month', 'week', 'day']" label="View" />
</v-col>
</v-row>
<v-row>
<v-col>
<v-switch v-model="showHeaderSlot" label="Header Slot" />
</v-col>
<v-col>
<v-switch v-model="showTitleSlot" label="Title Slot" />
</v-col>
<v-col v-if="view === 'month'">
<v-switch v-model="showDayTitleSlot" label="Day Title Slot" />
</v-col>
<v-col v-if="view === 'month'">
<v-switch v-model="showDayBodySlot" label="Day Body Slot" />
</v-col>
<v-col v-if="view === 'month'">
<v-switch v-model="showDayEventSlot" label="Day Event Slot" />
</v-col>
<v-col v-if="view === 'week'">
<v-switch v-model="showIntervalTitleSlot" label="Interval Title Slot" />
</v-col>
</v-row>
<v-row>
<v-col>
<v-calendar
v-model="thisDate"
:events="events"
:view-mode="view"
@click:date="clickedDate"
@click:day="clickedDay"
@click:event="clickedEvent"
@click:interval="clickedInterval"
@click:interval-date="clickedIntervalDate"
@next="clickedNext"
@prev="clickedPrev"
@today="clickedToday"
>
<template v-if="showHeaderSlot" #header="{ title }">
<span>{{ `Header ${title}` }}</span>
</template>
<template v-if="showTitleSlot" #title="{ title }">
<span>Test {{ title }}</span>
</template>
<template v-if="showDayTitleSlot" #dayTitle="{ title }">
{{ `Test ${title}` }}
</template>
<template v-if="showDayBodySlot" #dayBody="props">
<span>{{ props }}</span>
</template>
<template v-if="showDayEventSlot" #dayEvent="{ event }">
<v-sheet color="green">{{ event.title }}</v-sheet>
</template>
<template v-if="showIntervalTitleSlot" #intervalTitle="{ interval }">
<span>Test {{ adapter.format(interval.start, 'hours24h') }}</span>
</template>
</v-calendar>
</v-col>
</v-row>
</v-container>
</v-main>
</v-app>
</template>
<script setup>
import { ref } from 'vue'
import { useDate } from 'vuetify'
const adapter = useDate()
const thisDate = ref([new Date()])
const events = ref([
{
start: new Date(),
end: adapter.addHours(new Date(), 3),
title: 'Event 1',
color: 'green',
},
])
const view = ref('month')
const showHeaderSlot = ref(false)
const showTitleSlot = ref(false)
const showDayTitleSlot = ref(false)
const showDayBodySlot = ref(false)
const showDayEventSlot = ref(false)
const showIntervalTitleSlot = ref(false)
// TODO: Not Working
const clickedDate = function (data) {
console.log('clicked Date', data)
}
const clickedDay = function (data) {
console.log('clicked Day', data)
}
// TODO Not Working
const clickedEvent = function (data) {
console.log('clicked Event', data)
}
// TODO: Not Working
const clickedInterval = function (data) {
console.log('clicked interval', data)
}
const clickedIntervalDate = function (data) {
console.log('clicked Interval Date', data)
}
const clickedPrev = function (data) {
console.log('clicked prev', data)
}
const clickedNext = function (data) {
console.log('clicked next', data)
}
const clickedToday = function (data) {
console.log('clicked today', data)
}
</script>
@nekosaur I started this code a few weeks ago, but wasn't able to get it working. I've tried to match what you PR'd in #19555. But I still don't see the slots overriding content. This PRs also addresses the missing event handling and more slots.
Is there support for <slot> in jsx?
No.
Here is my solution for #19624 : I just count the 'v-chip__content' (in month-day format) on the screen. When you fetch monthly data from the server, if you retrieve it sorted by date and time, you can know which event you are currently clicking on. This is the code to find the index of the event on the screen and print it with console.log. Just you know, my current code is a temporary solution until Vuetify further develops the data format for the calendar.
findElementIndex(event) {
const clickedElement = event.target.closest('.v-chip__content');
if (!clickedElement) {
console.log('Clicked element is not a .v-chip__content element');
return;
}
const allElements = Array.from(document.querySelectorAll('.v-chip__content'));
const elementIndex = allElements.indexOf(clickedElement);
console.log('Clicked .v-chip__content Element Index:', elementIndex);
}
I rebased and pushed some changes
Any news on this merge request? It would be realy nice to have the event slot working again.
Need help with events and torture testing slots.
Any news on this merge request?