在日历外输入后,使用来自 API 的数据更新完整日历 Vue 事件

Update Full calendar Vue events with data from API after an input outside the calendar

我将 FullCalendar 包用作 Vue component (docs)。我有一个带有 select 输入和日历组件的表单。

仅当此 select 输入有值或发生更改时,我想通过发出 API 请求来设置日历上的事件,该请求向我返回链接到此值的事件select 输入。发出此请求后,我想将我的日历事件更新为从我的 API 电话中收到的事件。

更新事件后,我尝试在 calendarApi 上使用 render()refetch-events,但没有发生任何更新。

我怎样才能做到这一点?

代码:

<template>
    <div>
        <div class="card">
            <card-item :label-name="translations.labels.building" :error="errors.building" required="true"
                       :help-text="null">
                <multiselect v-model="buildingValue" @select="onBuildingChange" :options="buildings" :searchable="true"
                             track-by="id"
                             label="name"
                             optionsLimit="3"
                             openDirection="bottom"
                             :placeholder="translations.placeholders.building">
                </multiselect>
            </card-item>
            <card-item :label-name="translations.labels.date" :error="errors.date" required="true" :help-text="null">
                <FullCalendar ref="calendar" :options="calendarOptions"/>
            </card-item>
        </div>
    </div>
</template>

我的方法:

<script>
import {Durations} from "../enums/durations";
import CardItem from "./CardItem";
import FullCalendar from '@fullcalendar/vue';
import dayGridPlugin from '@fullcalendar/daygrid';
import interactionPlugin from '@fullcalendar/interaction';
import momentPlugin from '@fullcalendar/moment';

const DateFormat = "YYYY-MM-DD"
const InitialState = () => {
    return {
        durationValue: '',
        buildingValue: '',
        errors: {date: null, duration: null, building: null},
        durationOptions: Object.values(Durations).map((duration) => duration),
        calendarOptions: {
            visibleRange: {
                start: moment().format(DateFormat),
                end: moment().add(1, 'month').format(DateFormat)
            },
            plugins: [dayGridPlugin, interactionPlugin, momentPlugin],
            headerToolbar: {
                start: 'title',
                center: '',
                end: ''
            },
            titleFormat: '{MMMM {D}}, YYYY',
            initialView: 'dayGrid',
            weekends: true,
            editable: true,
            events: []
        },
    }
}

export default {
    name: "SingleReservation",
    props: ['buildings', 'types', 'companies', 'user', 'translations'],
    components: {
        CardItem,
        FullCalendar
    },
    data() {
        return InitialState()
    },
    methods: {
        onBuildingChange(building) {
            this.getEventsForBuilding(building)
        },
        async getEventsForBuilding(building) {
            try {
                if (building) {
                    console.log('id', building.id);
                    let {data} = await Nova.request().get(`/nova-vendor/reservation/building-capacities?searchValue=${building.id}`)
                    this.$data.calendarOptions.events = data;
                    this.$refs.calendar.$emit('refetch-events')
                } else {
                    // if no building
                }
            } catch (error) {
                this.$toasted.show('Something went wrong while getting events', {type: 'error'})
            }
        }
    },
}
</script>

更新组件的方法之一是给它一个密钥:

<template>
  <FullCalendar :key="calendarKey" :options="calendarOptions"/>
</template>

收到事件后,更改密钥(我使用 nanoid 包生成 ID):

<script>
  ...
  async getEventsForBuilding(building) {
    try {
      this.calendarOptions.events = data;
      this.calendarKey = nanoid(20);
    } catch (error) {
    ...
  },
  ...
</script>