<template> <div> <b-modal ref="modalEmissionManagerEdit" title="Edit a schedule" size="lg" > <p v-if="loaded.shows"> Schedule for: <b>{{ selectedShow.name }}</b> </p> <div v-if="timeslot && loaded.schedule"> This timeslot starts at <b-badge variant="info"> {{ prettyDateTime(timeslot.start) }} </b-badge> and ends at <b-badge variant="info"> {{ prettyDateTime(timeslot.end) }} </b-badge> <div v-if="schedule.rrule === 1"> <p> This is a single emission. <span v-if="!loaded.scheduleTimeslots"> <br> <img src="/assets/radio.gif" alt="loading schedule data" > </span> <span v-else> <span v-if="scheduleTimeslots.length > 1"> But due to a previous conflict resolution there is a second timeslot, from <b-badge variant="info"> <span v-if="timeslot.start === scheduleTimeslots[0].start">{{ prettyDateTime(scheduleTimeslots[1].start) }}</span> <span v-else>{{ prettyDateTime(scheduleTimeslots[0].start) }}</span> </b-badge> to <b-badge variant="info"> <span v-if="timeslot.start === scheduleTimeslots[0].start">{{ prettyDateTime(scheduleTimeslots[1].end) }}</span> <span v-else>{{ prettyDateTime(scheduleTimeslots[0].end) }}</span> </b-badge> . </span> <span v-else>No other timeslots in this schedule.</span> </span> </p> </div> <div v-else> <p>This is a recurring event: <b>{{ rruleRender(schedule.rrule) }}</b>, until: {{ prettyDate(schedule.until) }}</p> <p>All timeslots of this schedule:</p> <b-table id="emission-table" striped :per-page="perPage" :current-page="currentPage" :fields="['start', 'end']" :items="scheduleTimeslots" :busy="!loaded.scheduleTimeslots" :tbody-tr-class="trClass" > <template v-slot:cell(start)="data"> {{ prettyDateTime(data.item.start) }} </template> <template v-slot:cell(end)="data"> {{ prettyDateTime(data.item.end) }} </template> </b-table> <div class="tw-w-full tw-flex tw-justify-end"> <b-pagination v-model="currentPage" :total-rows="scheduleTimeslots.length" :per-page="perPage" aria-controls="emission-table" /> </div> </div> </div> <div v-else> <img src="/assets/radio.gif" alt="loading schedule data" > </div> <hr> <h4>Add repetition of schedule</h4> <b-row> <b-col cols="6"> <label class="tw-leading-loose"> When to repeat? <b-form-select v-model="repetitionRule" :options="repetitionOptions" /> </label> <b-checkbox v-model="useSameTime"> Use same start and end time </b-checkbox> </b-col> <b-col v-if="!useSameTime" cols="6" > <label class="tw-leading-loose"> Repeat at <b-form-input type="time" /> </label> </b-col> </b-row> <b-row v-if="repetitionRule === 3" class="tw-mt-4" > <b-col cols="6"> <label class="tw-leading-loose"> How many days later? <b-form-input v-model="addNoOfDays" type="number" /> </label> <b-checkbox v-model="onlyBusinessDays"> Only count business days </b-checkbox> </b-col> </b-row> <b-row class="mt-4"> <b-col> <b-button variant="primary" size="sm" @click="createRepetitionSchedule" > Create repetition schedule </b-button> </b-col> </b-row> <template v-slot:modal-footer> <div v-if="loaded.scheduleTimeslots" class="tw-w-full tw-flex tw-justify-between tw-items-center" > <div class="tw-space-x-2"> <b-button variant="danger" size="sm" @click="deleteFullSchedule(schedule.id)" > <span v-if="scheduleTimeslots.length === 1">Delete</span> <span v-else-if="schedule.rrule === 1">Delete both</span> <span v-else>Delete schedule and all timeslots</span> </b-button> <b-button v-if="schedule.rrule > 1 && scheduleTimeslots.length > 1" variant="danger" size="sm" @click="deleteSingleTimeslot(schedule.id, timeslot.id)" > Delete this timeslot </b-button> <b-button v-if="schedule.rrule > 1 && scheduleTimeslots.length > 1" variant="danger" size="sm" @click="deleteAllFutureTimeslots(schedule.id, timeslot.id)" > Delete all timeslots </b-button> </div> </div> <div v-else> <img src="/assets/radio.gif" alt="loading timeslot data" > </div> </template> </b-modal> <b-modal ref="modalEmissionManagerDeleteTimeslots" title="Deleting timeslots" size="lg" centered hide-footer no-close-on-esc no-close-on-backdrop > <div> <img src="/assets/radio.gif" alt="loading schedule data" > <b-progress :value="deletion.count" :max="deletion.amount" variant="info" animated /> </div> </b-modal> </div> </template> <script> import { mapGetters } from 'vuex' import prettyDate from '../../mixins/prettyDate' import rrules from '../../mixins/rrules' export default { mixins: [ prettyDate, rrules ], data () { return { currentPage: 1, perPage: 5, timeslot: null, deletion: { amount: 0, count: 0, }, useSameTime: true, onlyBusinessDays: false, addNoOfDays: 1, repetitionRule: 1, repetitionOptions: [ { value: 1, text: "On the following day" }, { value: 2, text: "On the following business day" }, { value: 3, text: "Number of days later" }, { value: 4, text: "Custom (WIP)" }, ] } }, computed: { loaded () { return { shows: this.$store.state.shows.loaded.shows, schedule: this.$store.state.shows.loaded.schedule, scheduleTimeslots: this.$store.state.shows.loaded.scheduleTimeslots, } }, ...mapGetters({ selectedShow: 'shows/selectedShow', schedule: 'shows/schedule', scheduleTimeslots: 'shows/scheduleTimeslots', }) }, methods: { trClass(item, type) { if (!item || type !== 'row') { return ''; } return item.id === this.timeslot.id ? 'table-info' : '' }, createRepetitionSchedule() { const { onlyBusinessDays, addNoOfDays } = this.getRepetitionParameters(); const { dstart, tstart, tend, rrule, until, fallback_id, automation_id, byweekday } = this.schedule; const newSchedule = { schedule: { dstart, tstart, tend, rrule, until, fallback_id, automation_id, byweekday, is_repetition: true, add_business_days_only: onlyBusinessDays, add_days_no: addNoOfDays, } }; this.$store.dispatch('shows/submitSchedule', { showId: this.selectedShow.id, schedule: newSchedule, callback: (response) => { if (response.data.projected === undefined) { this.$parent.renderView(null) } else { this.$log.debug('Timeslot conflict. Switching to resolve mode.'); this.$parent.resolve(response.data) } this.$refs.modalEmissionManagerEdit.hide() }, }); }, deleteFullSchedule (id) { this.$store.dispatch('shows/deleteSchedule', { show: this.selectedShow.id, schedule: id, callback: () => { this.$refs.modalEmissionManagerEdit.hide(); this.$parent.renderView(null) } }) }, deleteSingleTimeslot (scheduleId, timeslotId) { this.$store.dispatch('shows/deleteTimeslot', { show: this.selectedShow.id, schedule: scheduleId, timeslot: timeslotId, callback: () => { this.$refs.modalEmissionManagerEdit.hide() this.$parent.renderView(null) } }) }, deleteAllFutureTimeslots (scheduleId) { let startDate = new Date(this.timeslot.start) let toDelete = [] for (let slot of this.scheduleTimeslots) { if (new Date(slot.start) >= startDate) { toDelete.push(slot.id) } } if (toDelete.length === this.scheduleTimeslots.length) { this.$log.debug('deleting full schedule') this.deleteFullSchedule(scheduleId) } else { this.deletion.amount = toDelete.length this.deletion.count = 0 this.$refs.modalEmissionManagerDeleteTimeslots.show() for (let i in toDelete) { this.$log.debug('Deleting timeslot', toDelete[i]) this.$store.dispatch('shows/deleteTimeslot', { show: this.selectedShow.id, schedule: scheduleId, timeslot: toDelete[i], callback: () => { this.deletion.count++ this.$log.debug('deleted ' + this.deletion.count + ' timeslots') if (this.deletion.count === this.deletion.amount) { this.$parent.renderView(null) this.$refs.modalEmissionManagerDeleteTimeslots.hide() this.$refs.modalEmissionManagerEdit.hide() } } }) } } }, loadSchedule (scheduleId) { this.$store.dispatch('shows/fetchSchedule', { show: this.selectedShow.id, schedule: scheduleId, callback: () => { this.loadScheduleTimeslots(scheduleId) } }) }, loadScheduleTimeslots (scheduleId) { this.$store.dispatch('shows/fetchTimeslots', { id: this.selectedShow.id, schedule: scheduleId, start: this.schedule.dstart, end: this.schedule.until, }) }, getRepetitionParameters() { if (this.repetitionRule == 1) { return { onlyBusinessDays: false, addNoOfDays: 1, } } if (this.repetitionRule == 2) { return { onlyBusinessDays: true, addNoOfDays: 1, } } return { onlyBusinessDays: this.onlyBusinessDays, addNoOfDays: this.addNoOfDays, } }, // initialise a new schedule and open the modal open (timeslot) { this.timeslot = timeslot this.$refs.modalEmissionManagerEdit.show() this.loadSchedule(timeslot.schedule) }, } } </script> <style scoped> </style>