1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
|
// js/calendar.js
document.addEventListener('DOMContentLoaded', function () {
const calendarEl = getElementOrThrow('calendar');
const modal = getElementOrThrow('event_modal');
let selected_start_string = null;
const calendar = new FullCalendar.Calendar(calendarEl, {
editable: true,
locale: 'fr',
//timeZone: 'local', // à modifier pour être à l'heure d'un autre pays
initialView: 'dayGridMonth',
headerToolbar: {
left: 'prev,next today',
center: 'title',
//right: 'dayGridMonth,timeGridWeek,timeGridDay,listWeek'
right: 'dayGridMonth,timeGridWeek,listWeek'
},
slotMinWidth: 70,
defaultAllDay: false,
// numéros de semaine
//weekNumbers: true,
//weekText: 's',
// vue mois
contentHeight: 600, // après initialisation: calendar.setOption('contentHeight', 650);
//aspectRatio: 1.5, // après initialisation: calendar.setOption('aspectRatio', 1.8);
// pour recalculer la taille au redimensionnement du parent, exécuter: calendar.updateSize()
stickyHeaderDates: true, // garder les en-tête de colonnes lors du scroll
fixedWeekCount: false, // avec false, affiche 4, 5 ou 6 semaines selon le mois
selectable: true, // sélection de jours en cliquant dessus
longPressDelay: 300, // 1000ms par défaut
navLinks: true, // numéros de jour et de semaines clicables
// vue semaine
slotEventOverlap: true, // superposition (limitée) de deux évènements simultanés
allDayContent: 'Journée', // texte dans la case "toute la journée"
nowIndicator: true, // barre rouge pour maintenant
// params en plus: https://fullcalendar.io/docs/events-json-feed
events: 'index.php?action=get_events', // fichier PHP qui retourne les événements
select: function (info) {
selected_start_string = info.startStr; // variable "globale"
hideModal();
},
// sélection d'une date simple sur mobile, évite des problèmes de conflit avec eventClick
dateClick: function (info) {
if (window.matchMedia('(pointer: coarse)').matches) {
const end = new Date(info.date.getTime());
calendar.view.type === 'dayGridMonth' ? end.setDate(end.getDate() + 1) : end.setMinutes(end.getMinutes() + 30);
// vue date: la fin est une date exclue
// vue semaine: durée de 30min par défaut
calendar.select(info.date, end); // appeler select() avec un seul paramètre ne marche pas avec la vue "mois"
}
},
//unselect: function(event, view){},
eventClick: function (info) {
if (!info.event.start || !info.event.end) {
throw new Error('modale non conforme');
}
const modal_view = new CalendarModalView({
mode: 'show',
title: info.event.title,
description: info.event.extendedProps.description,
color: info.event.backgroundColor,
all_day: info.event.allDay,
start: info.event.start,
end: info.event.end
});
modal.innerHTML = modal_view.getView();
calendar.updateSize();
},
viewDidMount: function (_info) {
hideModal();
if (selected_start_string) {
calendar.gotoDate(new Date(selected_start_string));
}
},
//datesSet: function(info){}, // déclenché lorsque des dates affichées sont chargées (= comme viewDidMount + changement de date)
});
function hideModal() {
modal.innerHTML = '';
calendar.updateSize();
}
document.addEventListener('keydown', function (event) {
if (event.key === 'Escape') {
hideModal();
}
});
// technique de la délégation d'événements pour utiliser un bouton ajouté dynamiquement
document.addEventListener('click', function (event) {
if (!event.target) {
throw new Error('évènement click non conforme');
}
assertElementType(event.target, HTMLElement);
if (event.target.classList.contains('event_close_button')) {
hideModal();
}
});
calendar.render();
});
|