pep malade
This commit is contained in:
+113
-14
@@ -65,6 +65,10 @@ require __DIR__ . '/header.php';
|
|||||||
<div class="pf-legend-color fc-legend-avis"></div>
|
<div class="pf-legend-color fc-legend-avis"></div>
|
||||||
<span>Avis</span>
|
<span>Avis</span>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="pf-legend-item">
|
||||||
|
<div class="pf-legend-color fc-legend-pep-sick"></div>
|
||||||
|
<span>Pep malade</span>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@@ -134,26 +138,121 @@ require __DIR__ . '/header.php';
|
|||||||
<!-- ===================================================================== -->
|
<!-- ===================================================================== -->
|
||||||
<section class="pf-section">
|
<section class="pf-section">
|
||||||
<h2>Planning par semaine</h2>
|
<h2>Planning par semaine</h2>
|
||||||
<div class="pf-table-wrapper">
|
<div class="pf-table-wrapper" id="planningTable-wrapper">
|
||||||
<table id="planningTable" class="pf-table pf-table--compact">
|
<table id="planningHeaderTable" class="pf-table pf-table--compact">
|
||||||
|
<colgroup>
|
||||||
|
<col class="col-month"> <!-- Mois -->
|
||||||
|
<col class="col-month"> <!-- Semaine -->
|
||||||
|
<col class="col-day"> <!-- Lundi -->
|
||||||
|
<col class="col-day"> <!-- Mardi -->
|
||||||
|
<col class="col-day"> <!-- Mercredi -->
|
||||||
|
<col class="col-day"> <!-- Jeudi -->
|
||||||
|
<col class="col-day"> <!-- Vendredi -->
|
||||||
|
<col class="col-total"> <!-- # Off -->
|
||||||
|
<col class="col-total"> <!-- # Extra -->
|
||||||
|
<col class="col-total"> <!-- # Centre -->
|
||||||
|
<col class="col-total"> <!-- # Avis -->
|
||||||
|
<col class="col-total"> <!-- # Pep malade -->
|
||||||
|
<col class="col-total"> <!-- # Pep Présence -->
|
||||||
|
<!-- ALEX (6 colonnes) -->
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<!-- LAIA (6 colonnes) -->
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
</colgroup>
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>Mois</th>
|
<th rowspan="3" class="col-month">Mois</th>
|
||||||
<th>Semaine</th>
|
<th rowspan="3" class="col-month">Semaine</th>
|
||||||
<th>Lundi</th>
|
<th rowspan="3" class="col-day">Lundi</th>
|
||||||
<th>Mardi</th>
|
<th rowspan="3" class="col-day">Mardi</th>
|
||||||
<th>Mercredi</th>
|
<th rowspan="3" class="col-day">Mercredi</th>
|
||||||
<th>Jeudi</th>
|
<th rowspan="3" class="col-day">Jeudi</th>
|
||||||
<th>Vendredi</th>
|
<th rowspan="3" class="col-day">Vendredi</th>
|
||||||
<th># Off Carole</th>
|
<th rowspan="3" class="col-total"># Off Carole</th>
|
||||||
<th># Extra off Carole</th>
|
<th rowspan="3" class="col-total"># Extra off Carole</th>
|
||||||
<th>#Centre</th>
|
<th rowspan="3" class="col-total"># Centre</th>
|
||||||
<th>#Avis</th>
|
<th rowspan="3" class="col-total"># Avis</th>
|
||||||
|
<th rowspan="3" class="col-total"># Pep malade</th>
|
||||||
|
<th rowspan="3" class="col-total"># Pep Présence</th>
|
||||||
|
|
||||||
|
<!-- Ligne 1 : ALEX / LAIA -->
|
||||||
|
<th colspan="6" class="col-alex">ALEX</th>
|
||||||
|
<th colspan="6" class="col-laia">LAIA</th>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<!-- Ligne 2 : CP / JRA / JA (regroupement) -->
|
||||||
|
<th colspan="2" class="col-alex-sub">CP</th>
|
||||||
|
<th colspan="2" class="col-alex-sub">JRA</th>
|
||||||
|
<th colspan="2" class="col-alex-sub">JA</th>
|
||||||
|
|
||||||
|
<th colspan="2" class="col-laia-sub">CP</th>
|
||||||
|
<th colspan="2" class="col-laia-sub">JRA</th>
|
||||||
|
<th colspan="2" class="col-laia-sub">JA</th>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<!-- Ligne 3 : Available / Use pour chaque type -->
|
||||||
|
<!-- ALEX -->
|
||||||
|
<th class="col-alex-sub">Av.</th>
|
||||||
|
<th class="col-alex-sub">Use</th>
|
||||||
|
<th class="col-alex-sub">Av.</th>
|
||||||
|
<th class="col-alex-sub">Use</th>
|
||||||
|
<th class="col-alex-sub">Av.</th>
|
||||||
|
<th class="col-alex-sub">Use</th>
|
||||||
|
|
||||||
|
<!-- LAIA -->
|
||||||
|
<th class="col-laia-sub">Av.</th>
|
||||||
|
<th class="col-laia-sub">Use</th>
|
||||||
|
<th class="col-laia-sub">Av.</th>
|
||||||
|
<th class="col-laia-sub">Use</th>
|
||||||
|
<th class="col-laia-sub">Av.</th>
|
||||||
|
<th class="col-laia-sub">Use</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
|
</table>
|
||||||
|
<table id="planningTable" class="pf-table pf-table--compact">
|
||||||
<tbody id="planningBody">
|
<tbody id="planningBody">
|
||||||
<!-- Le contenu de ce tableau est entièrement généré par family-calendar.js -->
|
<colgroup>
|
||||||
|
<col class="col-month"> <!-- Mois -->
|
||||||
|
<col class="col-month"> <!-- Semaine -->
|
||||||
|
<col class="col-day"> <!-- Lundi -->
|
||||||
|
<col class="col-day"> <!-- Mardi -->
|
||||||
|
<col class="col-day"> <!-- Mercredi -->
|
||||||
|
<col class="col-day"> <!-- Jeudi -->
|
||||||
|
<col class="col-day"> <!-- Vendredi -->
|
||||||
|
<col class="col-total"> <!-- # Off -->
|
||||||
|
<col class="col-total"> <!-- # Extra -->
|
||||||
|
<col class="col-total"> <!-- # Centre -->
|
||||||
|
<col class="col-total"> <!-- # Avis -->
|
||||||
|
<col class="col-total"> <!-- # Pep malade -->
|
||||||
|
<col class="col-total"> <!-- # Pep Présence -->
|
||||||
|
<!-- ALEX (6 colonnes) -->
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<col class="col-alex-sub">
|
||||||
|
<!-- LAIA (6 colonnes) -->
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
<col class="col-laia-sub">
|
||||||
|
</colgroup>
|
||||||
|
<!-- lignes générées par JS -->
|
||||||
</tbody>
|
</tbody>
|
||||||
|
|
||||||
</table>
|
</table>
|
||||||
|
|
||||||
<!-- Le menu contextuel est caché par défaut et son contenu est généré par JS -->
|
<!-- Le menu contextuel est caché par défaut et son contenu est généré par JS -->
|
||||||
|
|||||||
@@ -29,44 +29,106 @@
|
|||||||
|
|
||||||
#planningTable th,
|
#planningTable th,
|
||||||
#planningTable td {
|
#planningTable td {
|
||||||
|
height: 32px;
|
||||||
|
min-height: 32px;
|
||||||
|
position: relative;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
white-space: nowrap;
|
white-space: nowrap;
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
text-overflow: ellipsis;
|
text-overflow: ellipsis;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Colonnes "Mois" et "Semaine" plus étroites */
|
/* Mois / Semaine */
|
||||||
#planningTable th:nth-child(1),
|
#planningHeaderTable .col-month,
|
||||||
#planningTable td:nth-child(1),
|
#planningTable .col-month {
|
||||||
#planningTable th:nth-child(2),
|
width: 60px;
|
||||||
#planningTable td:nth-child(2) {
|
max-width: 60px;
|
||||||
width: 2%;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Colonnes jours (Lundi à Vendredi) */
|
/* Jours */
|
||||||
#planningTable th:nth-child(3),
|
#planningHeaderTable .col-day,
|
||||||
#planningTable td:nth-child(3),
|
#planningTable .col-day {
|
||||||
#planningTable th:nth-child(4),
|
width: 70px;
|
||||||
#planningTable td:nth-child(4),
|
max-width: 70px;
|
||||||
#planningTable th:nth-child(5),
|
|
||||||
#planningTable td:nth-child(5),
|
|
||||||
#planningTable th:nth-child(6),
|
|
||||||
#planningTable td:nth-child(6),
|
|
||||||
#planningTable th:nth-child(7),
|
|
||||||
#planningTable td:nth-child(7) {
|
|
||||||
width: 2%;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Colonnes de totaux */
|
/* Totaux */
|
||||||
#planningTable th:nth-child(8),
|
#planningHeaderTable .col-total,
|
||||||
#planningTable td:nth-child(8),
|
#planningTable .col-total {
|
||||||
#planningTable th:nth-child(9),
|
width: 50px;
|
||||||
#planningTable td:nth-child(9),
|
max-width: 50px;
|
||||||
#planningTable th:nth-child(10),
|
white-space: nowrap;
|
||||||
#planningTable td:nth-child(10),
|
}
|
||||||
#planningTable th:nth-child(11),
|
|
||||||
#planningTable td:nth-child(11) {
|
/* Sous-colonnes Alex/Laia */
|
||||||
width: 4%;
|
#planningHeaderTable .col-alex-sub,
|
||||||
|
#planningHeaderTable .col-laia-sub,
|
||||||
|
#planningTable .col-alex-sub,
|
||||||
|
#planningTable .col-laia-sub {
|
||||||
|
width: 40px;
|
||||||
|
max-width: 40px;
|
||||||
|
font-size: 11px;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Autoriser le wrap dans les TH des sous-colonnes pour garder lisible */
|
||||||
|
#planningTable thead th.col-total,
|
||||||
|
#planningTable thead th.col-alex-sub,
|
||||||
|
#planningTable thead th.col-laia-sub {
|
||||||
|
white-space: normal;
|
||||||
|
}
|
||||||
|
|
||||||
|
#planningTable-wrapper {
|
||||||
|
max-height: 500px;
|
||||||
|
overflow-y: auto;
|
||||||
|
overflow-x: auto;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Header sticky */
|
||||||
|
#planningHeaderTable {
|
||||||
|
width: 100%;
|
||||||
|
border-collapse: collapse;
|
||||||
|
}
|
||||||
|
/* Empêcher le header de bouger/contracter */
|
||||||
|
#planningHeaderTable th {
|
||||||
|
background: #f0f4f8;
|
||||||
|
}
|
||||||
|
/* Optionnel : aligner visuellement les deux tableaux (bordures, etc.) */
|
||||||
|
#planningHeaderTable,
|
||||||
|
#planningTable {
|
||||||
|
width: 100%;
|
||||||
|
border-collapse: collapse;
|
||||||
|
table-layout: fixed;
|
||||||
|
}
|
||||||
|
|
||||||
|
#planningTable thead th {
|
||||||
|
top: 0;
|
||||||
|
z-index: 3;
|
||||||
|
background: #f0f4f8;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Ligne 1 */
|
||||||
|
#planningTable thead tr:nth-child(1) th {
|
||||||
|
position: sticky;
|
||||||
|
top: 0;
|
||||||
|
z-index: 3;
|
||||||
|
background: #f0f4f8;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Ligne 2 */
|
||||||
|
#planningTable thead tr:nth-child(2) th {
|
||||||
|
position: sticky;
|
||||||
|
top: 24px; /* hauteur de la 1ère ligne */
|
||||||
|
z-index: 3;
|
||||||
|
background: #f0f4f8;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Ligne 3 */
|
||||||
|
#planningTable thead tr:nth-child(3) th {
|
||||||
|
position: sticky;
|
||||||
|
top: 48px; /* 1ère + 2e ligne (22 + 22) */
|
||||||
|
z-index: 3;
|
||||||
|
background: #f0f4f8;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* === COLOR CODING / LÉGENDE === */
|
/* === COLOR CODING / LÉGENDE === */
|
||||||
@@ -189,6 +251,16 @@
|
|||||||
line-height: 1;
|
line-height: 1;
|
||||||
z-index: 2;
|
z-index: 2;
|
||||||
}
|
}
|
||||||
|
/* Planning hebdo : picto Centre en haut à droite */
|
||||||
|
#planningTable .fc-day--has-guard.fc-day--centre::after {
|
||||||
|
content: "🏫";
|
||||||
|
position: absolute;
|
||||||
|
top: 2px;
|
||||||
|
right: 2px;
|
||||||
|
font-size: 12px;
|
||||||
|
line-height: 1;
|
||||||
|
z-index: 2;
|
||||||
|
}
|
||||||
|
|
||||||
/* Combinaisons avec dégradés */
|
/* Combinaisons avec dégradés */
|
||||||
.fc-day--school-holiday.fc-day--off-carole {
|
.fc-day--school-holiday.fc-day--off-carole {
|
||||||
@@ -247,6 +319,33 @@
|
|||||||
content: "🏫";
|
content: "🏫";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.fc-legend-pep-sick {
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
font-size: 16px;
|
||||||
|
background: none;
|
||||||
|
border: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.fc-legend-pep-sick::before {
|
||||||
|
content: "🤒";
|
||||||
|
}
|
||||||
|
|
||||||
|
.fc-pep-sick-emoji {
|
||||||
|
position: absolute;
|
||||||
|
right: 2px;
|
||||||
|
bottom: 2px;
|
||||||
|
font-size: 14px;
|
||||||
|
line-height: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
#planningTable .fc-pep-sick-emoji {
|
||||||
|
font-size: 12px;
|
||||||
|
right: 2px;
|
||||||
|
bottom: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
/* Avis indicateur */
|
/* Avis indicateur */
|
||||||
.fc-legend-avis {
|
.fc-legend-avis {
|
||||||
border-radius: 2px;
|
border-radius: 2px;
|
||||||
|
|||||||
@@ -5,7 +5,8 @@
|
|||||||
document.addEventListener("DOMContentLoaded", () => {
|
document.addEventListener("DOMContentLoaded", () => {
|
||||||
const CONGE_TYPES = ["OFF_CAROLE", "EXTRA_OFF_CAROLE"];
|
const CONGE_TYPES = ["OFF_CAROLE", "EXTRA_OFF_CAROLE"];
|
||||||
const GUARDE_TYPES = ["CENTRE", "AVIS"];
|
const GUARDE_TYPES = ["CENTRE", "AVIS"];
|
||||||
const MODIFIABLE_TYPES = [...CONGE_TYPES, ...GUARDE_TYPES];
|
const PEP_TYPES = ["PEP_SICK"];
|
||||||
|
const MODIFIABLE_TYPES = [...CONGE_TYPES, ...GUARDE_TYPES, ...PEP_TYPES];
|
||||||
|
|
||||||
class FamilyCalendar {
|
class FamilyCalendar {
|
||||||
constructor() {
|
constructor() {
|
||||||
@@ -58,6 +59,13 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.events = [...this.dbEvents, ...this.fixedEvents];
|
this.events = [...this.dbEvents, ...this.fixedEvents];
|
||||||
this.leaves = await this.fetchLeaves();
|
this.leaves = await this.fetchLeaves();
|
||||||
|
|
||||||
|
// Nouveau : set des jours fériés (dates ISO)
|
||||||
|
this.publicHolidayDates = new Set(
|
||||||
|
this.fixedEvents
|
||||||
|
.filter((e) => e.type === "PUBLIC_HOLIDAY")
|
||||||
|
.map((e) => e.date)
|
||||||
|
);
|
||||||
|
|
||||||
this.reprocessAndRender();
|
this.reprocessAndRender();
|
||||||
this.renderMonthCalendar();
|
this.renderMonthCalendar();
|
||||||
}
|
}
|
||||||
@@ -77,7 +85,9 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
|
|
||||||
async fetchLeaves() {
|
async fetchLeaves() {
|
||||||
try {
|
try {
|
||||||
const res = await fetch("/api/get-leaves.php");
|
const res = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-leaves.php"
|
||||||
|
);
|
||||||
if (!res.ok) {
|
if (!res.ok) {
|
||||||
throw new Error("Erreur HTTP " + res.status);
|
throw new Error("Erreur HTTP " + res.status);
|
||||||
}
|
}
|
||||||
@@ -199,7 +209,14 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
|
|
||||||
reprocessEvents() {
|
reprocessEvents() {
|
||||||
this.weeks.forEach((w) => {
|
this.weeks.forEach((w) => {
|
||||||
w.totals = { offCarole: 0, extraOffCarole: 0, centre: 0, avis: 0 };
|
w.totals = {
|
||||||
|
offCarole: 0,
|
||||||
|
extraOffCarole: 0,
|
||||||
|
centre: 0,
|
||||||
|
avis: 0,
|
||||||
|
pepSick: 0,
|
||||||
|
presencePep: 0,
|
||||||
|
};
|
||||||
Object.values(w.dayFlags).forEach((df) => (df.eventsOnDay = []));
|
Object.values(w.dayFlags).forEach((df) => (df.eventsOnDay = []));
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -231,15 +248,44 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
case "AVIS":
|
case "AVIS":
|
||||||
week.totals.avis += dur;
|
week.totals.avis += dur;
|
||||||
break;
|
break;
|
||||||
|
case "PEP_SICK":
|
||||||
|
week.totals.pepSick += dur;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Calcul présence Pep par semaine
|
||||||
|
this.weeks.forEach((w) => {
|
||||||
|
// Calcul du nombre de jours potentiels d'accueil Pep dans la semaine
|
||||||
|
let workingDays = 0;
|
||||||
|
["mon", "tue", "wed", "thu", "fri"].forEach((dayKey) => {
|
||||||
|
const d = w.dayDates[dayKey];
|
||||||
|
const isoDate = `${d.getFullYear()}-${String(
|
||||||
|
d.getMonth() + 1
|
||||||
|
).padStart(2, "0")}-${String(d.getDate()).padStart(2, "0")}`;
|
||||||
|
|
||||||
|
const isPublicHoliday =
|
||||||
|
this.publicHolidayDates && this.publicHolidayDates.has(isoDate);
|
||||||
|
|
||||||
|
if (!isPublicHoliday) {
|
||||||
|
workingDays++;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
const absencesPep =
|
||||||
|
(w.totals.offCarole || 0) +
|
||||||
|
(w.totals.extraOffCarole || 0) +
|
||||||
|
(w.totals.pepSick || 0);
|
||||||
|
|
||||||
|
w.totals.presencePep = Math.max(0, workingDays - absencesPep);
|
||||||
|
w.totals.workingDays = workingDays; // si tu veux l'afficher un jour
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
updateGlobalSummary() {
|
updateGlobalSummary() {
|
||||||
const summaryDiv = document.getElementById("globalSummary");
|
const summaryDiv = document.getElementById("globalSummary");
|
||||||
if (!summaryDiv) return;
|
if (!summaryDiv) return;
|
||||||
|
|
||||||
// On filtre uniquement sur les événements "DB" pour le récap (pas les vacances/fériés)
|
|
||||||
const allEvents = this.dbEvents || [];
|
const allEvents = this.dbEvents || [];
|
||||||
|
|
||||||
const totalOff = allEvents
|
const totalOff = allEvents
|
||||||
@@ -250,9 +296,38 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
.filter((e) => e.type === "EXTRA_OFF_CAROLE")
|
.filter((e) => e.type === "EXTRA_OFF_CAROLE")
|
||||||
.reduce((sum, e) => sum + Number(e.duration || 1), 0);
|
.reduce((sum, e) => sum + Number(e.duration || 1), 0);
|
||||||
|
|
||||||
|
const totalPepSick = allEvents
|
||||||
|
.filter((e) => e.type === "PEP_SICK")
|
||||||
|
.reduce((sum, e) => sum + Number(e.duration || 1), 0);
|
||||||
|
|
||||||
|
// Calculer les jours ouvrés & présence Pep sur l'année scolaire
|
||||||
|
let totalWorkingDays = 0;
|
||||||
|
let totalPresencePep = 0;
|
||||||
|
|
||||||
|
// On parcourt l'année scolaire en mois, en réutilisant calculateMonthTotals
|
||||||
|
const start = new Date(2025, 8, 1); // 1 sept 2025
|
||||||
|
const end = new Date(2026, 7, 31); // 31 août 2026
|
||||||
|
|
||||||
|
const current = new Date(start);
|
||||||
|
while (current <= end) {
|
||||||
|
const y = current.getFullYear();
|
||||||
|
const m = current.getMonth();
|
||||||
|
const monthTotals = this.calculateMonthTotals(y, m);
|
||||||
|
|
||||||
|
totalWorkingDays += monthTotals.workingDays || 0;
|
||||||
|
totalPresencePep += monthTotals.presencePep || 0;
|
||||||
|
|
||||||
|
// Passer au 1er du mois suivant
|
||||||
|
current.setMonth(current.getMonth() + 1);
|
||||||
|
current.setDate(1);
|
||||||
|
}
|
||||||
|
|
||||||
summaryDiv.innerHTML = `
|
summaryDiv.innerHTML = `
|
||||||
<p><strong>Off Carole :</strong> ${totalOff} jours</p>
|
<p><strong>Off Carole :</strong> ${totalOff} jours</p>
|
||||||
<p><strong>Extra Off Carole :</strong> ${totalExtraOff} jours</p>
|
<p><strong>Extra Off Carole :</strong> ${totalExtraOff} jours</p>
|
||||||
|
<p><strong>Pep malade :</strong> ${totalPepSick} jours</p>
|
||||||
|
<p><strong>Jours potentiels d'accueil Pep (année scolaire, hors fériés) :</strong> ${totalWorkingDays}</p>
|
||||||
|
<p><strong>Présence Pep (année scolaire) :</strong> ${totalPresencePep} jours</p>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -294,20 +369,27 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.weeks.forEach((week) => {
|
this.weeks.forEach((week) => {
|
||||||
const tr = document.createElement("tr");
|
const tr = document.createElement("tr");
|
||||||
|
|
||||||
|
// Mois
|
||||||
if (!monthRowRendered[week.monthKey]) {
|
if (!monthRowRendered[week.monthKey]) {
|
||||||
monthRowRendered[week.monthKey] = true;
|
monthRowRendered[week.monthKey] = true;
|
||||||
const tdMonth = document.createElement("td");
|
const tdMonth = document.createElement("td");
|
||||||
tdMonth.rowSpan = monthSpans[week.monthKey] || 1;
|
tdMonth.rowSpan = monthSpans[week.monthKey] || 1;
|
||||||
tdMonth.textContent = week.monthName;
|
tdMonth.textContent = week.monthName;
|
||||||
|
tdMonth.classList.add("col-month");
|
||||||
tr.appendChild(tdMonth);
|
tr.appendChild(tdMonth);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Semaine
|
||||||
const tdWeek = document.createElement("td");
|
const tdWeek = document.createElement("td");
|
||||||
tdWeek.textContent = week.weekLabel;
|
tdWeek.textContent = week.weekLabel;
|
||||||
|
tdWeek.classList.add("col-month");
|
||||||
tr.appendChild(tdWeek);
|
tr.appendChild(tdWeek);
|
||||||
|
|
||||||
|
// Jours Lundi–Vendredi
|
||||||
["mon", "tue", "wed", "thu", "fri"].forEach((dayKey) => {
|
["mon", "tue", "wed", "thu", "fri"].forEach((dayKey) => {
|
||||||
const td = document.createElement("td");
|
const td = document.createElement("td");
|
||||||
|
td.classList.add("col-day");
|
||||||
|
|
||||||
const dayDate = week.dayDates[dayKey];
|
const dayDate = week.dayDates[dayKey];
|
||||||
td.dataset.date = `${dayDate.getFullYear()}-${String(
|
td.dataset.date = `${dayDate.getFullYear()}-${String(
|
||||||
dayDate.getMonth() + 1
|
dayDate.getMonth() + 1
|
||||||
@@ -317,9 +399,9 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
"0"
|
"0"
|
||||||
)}/${String(dayDate.getMonth() + 1).padStart(2, "0")}`;
|
)}/${String(dayDate.getMonth() + 1).padStart(2, "0")}`;
|
||||||
|
|
||||||
td.className = "";
|
|
||||||
let hasGarde = false;
|
let hasGarde = false;
|
||||||
let gardeType = null;
|
let gardeType = null;
|
||||||
|
let hasPepSick = false;
|
||||||
|
|
||||||
week.dayFlags[dayKey].eventsOnDay.forEach((evt) => {
|
week.dayFlags[dayKey].eventsOnDay.forEach((evt) => {
|
||||||
const classMap = {
|
const classMap = {
|
||||||
@@ -327,6 +409,7 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
PUBLIC_HOLIDAY: "fc-day--public-holiday",
|
PUBLIC_HOLIDAY: "fc-day--public-holiday",
|
||||||
OFF_CAROLE: "fc-day--off-carole",
|
OFF_CAROLE: "fc-day--off-carole",
|
||||||
EXTRA_OFF_CAROLE: "fc-day--extra-off-carole",
|
EXTRA_OFF_CAROLE: "fc-day--extra-off-carole",
|
||||||
|
// pas de couleur pour PEP_SICK dans l'hebdo
|
||||||
};
|
};
|
||||||
|
|
||||||
if (classMap[evt.type]) {
|
if (classMap[evt.type]) {
|
||||||
@@ -337,6 +420,10 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
hasGarde = true;
|
hasGarde = true;
|
||||||
gardeType = evt.type;
|
gardeType = evt.type;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (evt.type === "PEP_SICK") {
|
||||||
|
hasPepSick = true;
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
if (hasGarde) {
|
if (hasGarde) {
|
||||||
@@ -345,7 +432,14 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
if (gardeType === "AVIS") td.classList.add("fc-day--avis");
|
if (gardeType === "AVIS") td.classList.add("fc-day--avis");
|
||||||
}
|
}
|
||||||
|
|
||||||
// Indicateur congés Alex/Laia
|
if (hasPepSick) {
|
||||||
|
const pepSpan = document.createElement("span");
|
||||||
|
pepSpan.className = "fc-pep-sick-emoji";
|
||||||
|
pepSpan.textContent = "🤒";
|
||||||
|
td.appendChild(pepSpan);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Congés Alex/Laia
|
||||||
const isoDate = td.dataset.date;
|
const isoDate = td.dataset.date;
|
||||||
const leavesOnDay = this.leaves.filter(
|
const leavesOnDay = this.leaves.filter(
|
||||||
(lv) => lv.leave_date === isoDate
|
(lv) => lv.leave_date === isoDate
|
||||||
@@ -355,8 +449,8 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
const container = document.createElement("div");
|
const container = document.createElement("div");
|
||||||
container.className = "fc-leaves-label-container";
|
container.className = "fc-leaves-label-container";
|
||||||
|
|
||||||
const hasAlex = leavesOnDay.some((lv) => lv.person_id === 2); // Alex
|
const hasAlex = leavesOnDay.some((lv) => lv.person_id === 2);
|
||||||
const hasLaia = leavesOnDay.some((lv) => lv.person_id === 3); // Laia
|
const hasLaia = leavesOnDay.some((lv) => lv.person_id === 3);
|
||||||
|
|
||||||
if (hasAlex) {
|
if (hasAlex) {
|
||||||
const alexSpan = document.createElement("span");
|
const alexSpan = document.createElement("span");
|
||||||
@@ -378,22 +472,53 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
tr.appendChild(td);
|
tr.appendChild(td);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Totaux
|
||||||
const tdOff = document.createElement("td");
|
const tdOff = document.createElement("td");
|
||||||
tdOff.textContent = formatTotal(week.totals.offCarole);
|
tdOff.textContent = formatTotal(week.totals.offCarole);
|
||||||
|
tdOff.classList.add("col-total");
|
||||||
tr.appendChild(tdOff);
|
tr.appendChild(tdOff);
|
||||||
|
|
||||||
const tdExtra = document.createElement("td");
|
const tdExtra = document.createElement("td");
|
||||||
tdExtra.textContent = formatTotal(week.totals.extraOffCarole);
|
tdExtra.textContent = formatTotal(week.totals.extraOffCarole);
|
||||||
|
tdExtra.classList.add("col-total");
|
||||||
tr.appendChild(tdExtra);
|
tr.appendChild(tdExtra);
|
||||||
|
|
||||||
const tdCentre = document.createElement("td");
|
const tdCentre = document.createElement("td");
|
||||||
tdCentre.textContent = formatTotal(week.totals.centre);
|
tdCentre.textContent = formatTotal(week.totals.centre);
|
||||||
|
tdCentre.classList.add("col-total");
|
||||||
tr.appendChild(tdCentre);
|
tr.appendChild(tdCentre);
|
||||||
|
|
||||||
const tdAvis = document.createElement("td");
|
const tdAvis = document.createElement("td");
|
||||||
tdAvis.textContent = formatTotal(week.totals.avis);
|
tdAvis.textContent = formatTotal(week.totals.avis);
|
||||||
|
tdAvis.classList.add("col-total");
|
||||||
tr.appendChild(tdAvis);
|
tr.appendChild(tdAvis);
|
||||||
|
|
||||||
|
const tdPepSick = document.createElement("td");
|
||||||
|
tdPepSick.textContent = formatTotal(week.totals.pepSick);
|
||||||
|
tdPepSick.classList.add("col-total");
|
||||||
|
tr.appendChild(tdPepSick);
|
||||||
|
|
||||||
|
const tdPresencePep = document.createElement("td");
|
||||||
|
tdPresencePep.textContent = formatTotal(week.totals.presencePep);
|
||||||
|
tdPresencePep.classList.add("col-total");
|
||||||
|
tr.appendChild(tdPresencePep);
|
||||||
|
|
||||||
|
// 6 colonnes ALEX
|
||||||
|
for (let i = 0; i < 6; i++) {
|
||||||
|
const td = document.createElement("td");
|
||||||
|
td.textContent = "";
|
||||||
|
td.classList.add("col-alex-sub");
|
||||||
|
tr.appendChild(td);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 6 colonnes LAIA
|
||||||
|
for (let i = 0; i < 6; i++) {
|
||||||
|
const td = document.createElement("td");
|
||||||
|
td.textContent = "";
|
||||||
|
td.classList.add("col-laia-sub");
|
||||||
|
tr.appendChild(td);
|
||||||
|
}
|
||||||
|
|
||||||
this.planningBody.appendChild(tr);
|
this.planningBody.appendChild(tr);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -428,11 +553,6 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.monthSelectionMenu.addEventListener("click", (e) =>
|
this.monthSelectionMenu.addEventListener("click", (e) =>
|
||||||
this.handleMonthMenuClick(e)
|
this.handleMonthMenuClick(e)
|
||||||
);
|
);
|
||||||
|
|
||||||
// Gestion des actions bulk (bulk-update*, bulk-delete*) via handleMenuClick
|
|
||||||
this.monthSelectionMenu.addEventListener("click", (e) =>
|
|
||||||
this.handleMenuClick(e)
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -512,12 +632,14 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
);
|
);
|
||||||
const conge = eventsOnDay.find((ev) => CONGE_TYPES.includes(ev.type));
|
const conge = eventsOnDay.find((ev) => CONGE_TYPES.includes(ev.type));
|
||||||
const garde = eventsOnDay.find((ev) => GUARDE_TYPES.includes(ev.type));
|
const garde = eventsOnDay.find((ev) => GUARDE_TYPES.includes(ev.type));
|
||||||
|
const pep = eventsOnDay.find((ev) => PEP_TYPES.includes(ev.type));
|
||||||
|
|
||||||
if (!conge && !garde) {
|
if (!conge && !garde && !pep) {
|
||||||
this.showAddMenu(e);
|
this.showAddMenu(e);
|
||||||
} else {
|
} else {
|
||||||
this.showEditMenuForDay(e, { conge, garde, date });
|
this.showEditMenuForDay(e, { conge, garde, pep, date });
|
||||||
}
|
}
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -662,11 +784,13 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
<div class="fc-menu-section"><strong>Mode de Garde</strong></div>
|
<div class="fc-menu-section"><strong>Mode de Garde</strong></div>
|
||||||
<button data-action="add" data-type="CENTRE">Centre</button>
|
<button data-action="add" data-type="CENTRE">Centre</button>
|
||||||
<button data-action="add" data-type="AVIS">Avis</button>
|
<button data-action="add" data-type="AVIS">Avis</button>
|
||||||
|
<div class="fc-menu-section"><strong>Pep</strong></div>
|
||||||
|
<button data-action="add" data-type="PEP_SICK">Pep malade</button>
|
||||||
`;
|
`;
|
||||||
this.positionAndShowMenu(e);
|
this.positionAndShowMenu(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
showEditMenuForDay(e, { conge, garde, date }) {
|
showEditMenuForDay(e, { conge, garde, pep, date }) {
|
||||||
console.log(
|
console.log(
|
||||||
"[EDIT MENU] pour date",
|
"[EDIT MENU] pour date",
|
||||||
date,
|
date,
|
||||||
@@ -729,6 +853,24 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// --- Section Pep malade ---
|
||||||
|
let pepSection = "";
|
||||||
|
if (pep) {
|
||||||
|
pepSection = `
|
||||||
|
<div class="fc-menu-section"><strong>Pep</strong></div>
|
||||||
|
<button data-action="delete" data-event-id="${pep.id}">
|
||||||
|
Supprimer "Pep malade"
|
||||||
|
</button>
|
||||||
|
`;
|
||||||
|
} else {
|
||||||
|
pepSection = `
|
||||||
|
<div class="fc-menu-section"><strong>Pep</strong></div>
|
||||||
|
<button data-action="add-single" data-type="PEP_SICK" data-date="${date}">
|
||||||
|
Marquer Pep malade
|
||||||
|
</button>
|
||||||
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
// --- Section congés Alex / Laia ---
|
// --- Section congés Alex / Laia ---
|
||||||
console.log(
|
console.log(
|
||||||
"[EDIT MENU] this.leaves length =",
|
"[EDIT MENU] this.leaves length =",
|
||||||
@@ -770,7 +912,7 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
const fullHtml = congeSection + gardeSection + leavesSection;
|
const fullHtml = congeSection + gardeSection + pepSection + leavesSection;
|
||||||
console.log("[EDIT MENU] full menu HTML length =", fullHtml.length);
|
console.log("[EDIT MENU] full menu HTML length =", fullHtml.length);
|
||||||
|
|
||||||
this.selectionMenu.innerHTML = fullHtml;
|
this.selectionMenu.innerHTML = fullHtml;
|
||||||
@@ -835,17 +977,22 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
const res = await fetch("/api/manage-event.php", {
|
const res = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/manage-event.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify(payload),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify(payload),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!res.ok) {
|
if (!res.ok) {
|
||||||
const errData = await res.json().catch(() => ({}));
|
const errData = await res.json().catch(() => ({}));
|
||||||
throw new Error(errData.message || "Erreur HTTP " + res.status);
|
throw new Error(errData.message || "Erreur HTTP " + res.status);
|
||||||
}
|
}
|
||||||
|
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
@@ -885,11 +1032,14 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearSelection();
|
this.clearSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/save-leaves.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/save-leaves.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify([newLeave]),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify([newLeave]),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
throw new Error("Erreur HTTP " + response.status);
|
throw new Error("Erreur HTTP " + response.status);
|
||||||
}
|
}
|
||||||
@@ -917,11 +1067,14 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearSelection();
|
this.clearSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/manage-leaf.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/manage-leaf.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify({ action: "delete_day", date: leaveDate }),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify({ action: "delete_day", date: leaveDate }),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
const errData = await response.json().catch(() => ({}));
|
const errData = await response.json().catch(() => ({}));
|
||||||
throw new Error(
|
throw new Error(
|
||||||
@@ -985,17 +1138,22 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearSelection();
|
this.clearSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/save-events.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/save-events.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify(newEvents),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify(newEvents),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
throw new Error("Erreur HTTP " + response.status);
|
throw new Error("Erreur HTTP " + response.status);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Resync DB events
|
// Resync DB events
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
@@ -1050,16 +1208,21 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearSelection();
|
this.clearSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/save-events.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/save-events.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify([newEvent]),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify([newEvent]),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
throw new Error("Erreur HTTP " + response.status);
|
throw new Error("Erreur HTTP " + response.status);
|
||||||
}
|
}
|
||||||
|
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
@@ -1088,11 +1251,14 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearSelection();
|
this.clearSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/manage-event.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/manage-event.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify({ action: "delete", event_id: eventId }),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify({ action: "delete", event_id: eventId }),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
const errData = await response.json().catch(() => ({}));
|
const errData = await response.json().catch(() => ({}));
|
||||||
throw new Error(
|
throw new Error(
|
||||||
@@ -1100,7 +1266,9 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
@@ -1131,15 +1299,18 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearSelection();
|
this.clearSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/manage-event.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/manage-event.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify({
|
method: "POST",
|
||||||
action: "update",
|
headers: { "Content-Type": "application/json" },
|
||||||
event_id: eventId,
|
body: JSON.stringify({
|
||||||
new_type: newType,
|
action: "update",
|
||||||
}),
|
event_id: eventId,
|
||||||
});
|
new_type: newType,
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
const errData = await response.json().catch(() => ({}));
|
const errData = await response.json().catch(() => ({}));
|
||||||
throw new Error(
|
throw new Error(
|
||||||
@@ -1147,7 +1318,9 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
@@ -1168,17 +1341,22 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
|
|
||||||
async manageEvent(payload) {
|
async manageEvent(payload) {
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/manage-event.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/manage-event.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify(payload),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify(payload),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
const errData = await response.json().catch(() => ({}));
|
const errData = await response.json().catch(() => ({}));
|
||||||
throw new Error(errData.message || "Erreur HTTP " + response.status);
|
throw new Error(errData.message || "Erreur HTTP " + response.status);
|
||||||
}
|
}
|
||||||
|
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
@@ -1276,31 +1454,38 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
}
|
}
|
||||||
|
|
||||||
calculateMonthTotals(year, month) {
|
calculateMonthTotals(year, month) {
|
||||||
// Calculer le premier et dernier jour du mois (uniquement jours de semaine)
|
|
||||||
const firstDay = new Date(year, month, 1);
|
|
||||||
const lastDay = new Date(year, month + 1, 0);
|
const lastDay = new Date(year, month + 1, 0);
|
||||||
const totals = {
|
const totals = {
|
||||||
offCarole: 0,
|
offCarole: 0,
|
||||||
extraOffCarole: 0,
|
extraOffCarole: 0,
|
||||||
centre: 0,
|
centre: 0,
|
||||||
avis: 0,
|
avis: 0,
|
||||||
|
pepSick: 0,
|
||||||
|
presencePep: 0,
|
||||||
|
workingDays: 0, // jours potentiels d'accueil Pep
|
||||||
};
|
};
|
||||||
|
|
||||||
// Parcourir tous les jours du mois
|
|
||||||
for (let day = 1; day <= lastDay.getDate(); day++) {
|
for (let day = 1; day <= lastDay.getDate(); day++) {
|
||||||
const date = new Date(year, month, day);
|
const date = new Date(year, month, day);
|
||||||
const dayOfWeek = date.getDay();
|
const dayOfWeek = date.getDay(); // 0=dim, 6=sam
|
||||||
|
|
||||||
// Ignorer les samedi (6) et dimanche (0)
|
|
||||||
if (dayOfWeek === 0 || dayOfWeek === 6) {
|
if (dayOfWeek === 0 || dayOfWeek === 6) {
|
||||||
continue;
|
continue; // on saute samedi/dimanche
|
||||||
}
|
}
|
||||||
|
|
||||||
const isoDate = `${year}-${String(month + 1).padStart(2, "0")}-${String(
|
const isoDate = `${year}-${String(month + 1).padStart(2, "0")}-${String(
|
||||||
day
|
day
|
||||||
).padStart(2, "0")}`;
|
).padStart(2, "0")}`;
|
||||||
|
|
||||||
// Trouver les événements pour ce jour
|
// Si jour férié, ce n'est PAS un jour potentiel d'accueil Pep
|
||||||
|
const isPublicHoliday =
|
||||||
|
this.publicHolidayDates && this.publicHolidayDates.has(isoDate);
|
||||||
|
|
||||||
|
if (!isPublicHoliday) {
|
||||||
|
totals.workingDays++;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Événements de base (pf_events) pour ce jour
|
||||||
const dayEvents = this.dbEvents.filter((evt) => evt.date === isoDate);
|
const dayEvents = this.dbEvents.filter((evt) => evt.date === isoDate);
|
||||||
|
|
||||||
dayEvents.forEach((evt) => {
|
dayEvents.forEach((evt) => {
|
||||||
@@ -1318,17 +1503,27 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
case "AVIS":
|
case "AVIS":
|
||||||
totals.avis += dur;
|
totals.avis += dur;
|
||||||
break;
|
break;
|
||||||
|
case "PEP_SICK":
|
||||||
|
totals.pepSick += dur;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const absencesPep =
|
||||||
|
(totals.offCarole || 0) +
|
||||||
|
(totals.extraOffCarole || 0) +
|
||||||
|
(totals.pepSick || 0);
|
||||||
|
|
||||||
|
totals.presencePep = Math.max(0, totals.workingDays - absencesPep);
|
||||||
|
|
||||||
return totals;
|
return totals;
|
||||||
}
|
}
|
||||||
|
|
||||||
generateMonthSummaryHTML(year, month) {
|
generateMonthSummaryHTML(year, month) {
|
||||||
const totals = this.calculateMonthTotals(year, month);
|
const totals = this.calculateMonthTotals(year, month);
|
||||||
const formatTotal = (total) =>
|
const formatTotal = (total) =>
|
||||||
total > 0 ? (Number.isInteger(total) ? total : total.toFixed(1)) : "";
|
total > 0 ? (Number.isInteger(total) ? total : total.toFixed(1)) : "0";
|
||||||
|
|
||||||
const monthLabel = `${getMonthNameFr(month)} ${year}`;
|
const monthLabel = `${getMonthNameFr(month)} ${year}`;
|
||||||
|
|
||||||
@@ -1338,19 +1533,21 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>Mois</th>
|
<th>Mois</th>
|
||||||
|
<th>Jours ouvrés</th>
|
||||||
<th># Off Carole</th>
|
<th># Off Carole</th>
|
||||||
<th># Extra off Carole</th>
|
<th># Extra off Carole</th>
|
||||||
<th># Centre</th>
|
<th># Pep malade</th>
|
||||||
<th># Avis</th>
|
<th># Présence Pep</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody>
|
<tbody>
|
||||||
<tr>
|
<tr>
|
||||||
<td>${monthLabel}</td>
|
<td>${monthLabel}</td>
|
||||||
|
<td>${formatTotal(totals.workingDays)}</td>
|
||||||
<td>${formatTotal(totals.offCarole)}</td>
|
<td>${formatTotal(totals.offCarole)}</td>
|
||||||
<td>${formatTotal(totals.extraOffCarole)}</td>
|
<td>${formatTotal(totals.extraOffCarole)}</td>
|
||||||
<td>${formatTotal(totals.centre)}</td>
|
<td>${formatTotal(totals.pepSick)}</td>
|
||||||
<td>${formatTotal(totals.avis)}</td>
|
<td>${formatTotal(totals.presencePep)}</td>
|
||||||
</tr>
|
</tr>
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
@@ -1602,6 +1799,7 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
let classes = "fc-month-day";
|
let classes = "fc-month-day";
|
||||||
let hasGarde = false;
|
let hasGarde = false;
|
||||||
let gardeType = null;
|
let gardeType = null;
|
||||||
|
let hasPepSick = false; // <- ajouté
|
||||||
|
|
||||||
dayEvents.forEach((evt) => {
|
dayEvents.forEach((evt) => {
|
||||||
const classMap = {
|
const classMap = {
|
||||||
@@ -1609,6 +1807,7 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
PUBLIC_HOLIDAY: "fc-day--public-holiday",
|
PUBLIC_HOLIDAY: "fc-day--public-holiday",
|
||||||
OFF_CAROLE: "fc-day--off-carole",
|
OFF_CAROLE: "fc-day--off-carole",
|
||||||
EXTRA_OFF_CAROLE: "fc-day--extra-off-carole",
|
EXTRA_OFF_CAROLE: "fc-day--extra-off-carole",
|
||||||
|
// PEP_SICK: "fc-day--pep-sick",
|
||||||
};
|
};
|
||||||
|
|
||||||
if (classMap[evt.type]) {
|
if (classMap[evt.type]) {
|
||||||
@@ -1619,6 +1818,10 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
hasGarde = true;
|
hasGarde = true;
|
||||||
gardeType = evt.type;
|
gardeType = evt.type;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (evt.type === "PEP_SICK") {
|
||||||
|
hasPepSick = true;
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
if (hasGarde) {
|
if (hasGarde) {
|
||||||
@@ -1635,6 +1838,10 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
|
|
||||||
let cellInnerHTML = `${day}`;
|
let cellInnerHTML = `${day}`;
|
||||||
|
|
||||||
|
if (hasPepSick) {
|
||||||
|
cellInnerHTML += `<span class="fc-pep-sick-emoji">🤒</span>`;
|
||||||
|
}
|
||||||
|
|
||||||
if (leavesOnDay.length > 0) {
|
if (leavesOnDay.length > 0) {
|
||||||
const hasAlex = leavesOnDay.some((lv) => lv.person_id === 2); // Alex
|
const hasAlex = leavesOnDay.some((lv) => lv.person_id === 2); // Alex
|
||||||
const hasLaia = leavesOnDay.some((lv) => lv.person_id === 3); // Laia
|
const hasLaia = leavesOnDay.some((lv) => lv.person_id === 3); // Laia
|
||||||
@@ -1696,11 +1903,11 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
);
|
);
|
||||||
const conge = eventsOnDay.find((e) => CONGE_TYPES.includes(e.type));
|
const conge = eventsOnDay.find((e) => CONGE_TYPES.includes(e.type));
|
||||||
const garde = eventsOnDay.find((e) => GUARDE_TYPES.includes(e.type));
|
const garde = eventsOnDay.find((e) => GUARDE_TYPES.includes(e.type));
|
||||||
|
const pep = eventsOnDay.find((e) => PEP_TYPES.includes(e.type));
|
||||||
if (!conge && !garde) {
|
if (!conge && !garde && !pep) {
|
||||||
this.showMonthAddMenu(e);
|
this.showMonthAddMenu(e);
|
||||||
} else {
|
} else {
|
||||||
this.showMonthEditMenuForDay(e, { conge, garde, date });
|
this.showMonthEditMenuForDay(e, { conge, garde, pep, date });
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -1761,11 +1968,13 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
<div class="fc-menu-section"><strong>Mode de Garde</strong></div>
|
<div class="fc-menu-section"><strong>Mode de Garde</strong></div>
|
||||||
<button data-action="add" data-type="CENTRE">Centre</button>
|
<button data-action="add" data-type="CENTRE">Centre</button>
|
||||||
<button data-action="add" data-type="AVIS">Avis</button>
|
<button data-action="add" data-type="AVIS">Avis</button>
|
||||||
|
<div class="fc-menu-section"><strong>Pep</strong></div>
|
||||||
|
<button data-action="add" data-type="PEP_SICK">Pep malade</button>
|
||||||
`;
|
`;
|
||||||
this.positionAndShowMonthMenu(e);
|
this.positionAndShowMonthMenu(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
showMonthEditMenuForDay(e, { conge, garde, date }) {
|
showMonthEditMenuForDay(e, { conge, garde, pep, date }) {
|
||||||
if (!this.monthSelectionMenu) return;
|
if (!this.monthSelectionMenu) return;
|
||||||
|
|
||||||
// --- Section congé Carole ---
|
// --- Section congé Carole ---
|
||||||
@@ -1821,6 +2030,24 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// --- Section Pep malade ---
|
||||||
|
let pepSection = "";
|
||||||
|
if (pep) {
|
||||||
|
pepSection = `
|
||||||
|
<div class="fc-menu-section"><strong>Pep</strong></div>
|
||||||
|
<button data-action="delete" data-event-id="${pep.id}">
|
||||||
|
Supprimer "Pep malade"
|
||||||
|
</button>
|
||||||
|
`;
|
||||||
|
} else {
|
||||||
|
pepSection = `
|
||||||
|
<div class="fc-menu-section"><strong>Pep</strong></div>
|
||||||
|
<button data-action="add-single" data-type="PEP_SICK" data-date="${date}">
|
||||||
|
Marquer Pep malade
|
||||||
|
</button>
|
||||||
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
// --- Section congés Alex / Laia ---
|
// --- Section congés Alex / Laia ---
|
||||||
const leavesOnDay = (this.leaves || []).filter(
|
const leavesOnDay = (this.leaves || []).filter(
|
||||||
(lv) => lv.leave_date === date
|
(lv) => lv.leave_date === date
|
||||||
@@ -1858,7 +2085,7 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
|
|
||||||
// --- Assemblage du menu ---
|
// --- Assemblage du menu ---
|
||||||
this.monthSelectionMenu.innerHTML =
|
this.monthSelectionMenu.innerHTML =
|
||||||
congeSection + gardeSection + leavesSection;
|
congeSection + gardeSection + pepSection + leavesSection;
|
||||||
this.positionAndShowMonthMenu(e);
|
this.positionAndShowMonthMenu(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1978,16 +2205,21 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearMonthSelection();
|
this.clearMonthSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/save-events.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/save-events.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify(newEvents),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify(newEvents),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
throw new Error("Erreur HTTP " + response.status);
|
throw new Error("Erreur HTTP " + response.status);
|
||||||
}
|
}
|
||||||
|
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
@@ -2041,16 +2273,21 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearMonthSelection();
|
this.clearMonthSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/save-events.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/save-events.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify([newEvent]),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify([newEvent]),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
throw new Error("Erreur HTTP " + response.status);
|
throw new Error("Erreur HTTP " + response.status);
|
||||||
}
|
}
|
||||||
|
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
@@ -2077,11 +2314,14 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearMonthSelection();
|
this.clearMonthSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/manage-event.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/manage-event.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify({ action: "delete", event_id: eventId }),
|
method: "POST",
|
||||||
});
|
headers: { "Content-Type": "application/json" },
|
||||||
|
body: JSON.stringify({ action: "delete", event_id: eventId }),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
const errData = await response.json().catch(() => ({}));
|
const errData = await response.json().catch(() => ({}));
|
||||||
throw new Error(
|
throw new Error(
|
||||||
@@ -2089,7 +2329,9 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
@@ -2116,15 +2358,18 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
this.clearMonthSelection();
|
this.clearMonthSelection();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch("/api/manage-event.php", {
|
const response = await fetch(
|
||||||
method: "POST",
|
"/modules/family-calendar/includes/api/manage-event.php",
|
||||||
headers: { "Content-Type": "application/json" },
|
{
|
||||||
body: JSON.stringify({
|
method: "POST",
|
||||||
action: "update",
|
headers: { "Content-Type": "application/json" },
|
||||||
event_id: eventId,
|
body: JSON.stringify({
|
||||||
new_type: newType,
|
action: "update",
|
||||||
}),
|
event_id: eventId,
|
||||||
});
|
new_type: newType,
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
);
|
||||||
if (!response.ok) {
|
if (!response.ok) {
|
||||||
const errData = await response.json().catch(() => ({}));
|
const errData = await response.json().catch(() => ({}));
|
||||||
throw new Error(
|
throw new Error(
|
||||||
@@ -2132,7 +2377,9 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const resEvents = await fetch("/api/get-events.php");
|
const resEvents = await fetch(
|
||||||
|
"/modules/family-calendar/includes/api/get-events.php"
|
||||||
|
);
|
||||||
if (!resEvents.ok) {
|
if (!resEvents.ok) {
|
||||||
throw new Error("Erreur lors du rechargement des événements.");
|
throw new Error("Erreur lors du rechargement des événements.");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,17 @@
|
|||||||
|
[2026-01-06T14:39:28+01:00] RAW INPUT: []
|
||||||
|
[2026-01-06T14:39:28+01:00] RAW INPUT: [{"date":"2025-09-08","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T14:40:04+01:00] RAW INPUT: [{"date":"2025-09-30","type":"OFF_CAROLE","person":"Carole","duration":1}]
|
||||||
|
[2026-01-06T14:40:04+01:00] RAW INPUT: []
|
||||||
|
[2026-01-06T14:40:52+01:00] RAW INPUT: [{"date":"2025-09-08","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T14:40:52+01:00] RAW INPUT: []
|
||||||
|
[2026-01-06T14:46:35+01:00] RAW INPUT: [{"date":"2025-09-22","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T14:47:20+01:00] RAW INPUT: [{"date":"2025-09-29","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T14:48:43+01:00] RAW INPUT: [{"date":"2025-09-30","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T15:00:55+01:00] RAW INPUT: [{"date":"2025-09-29","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T15:04:46+01:00] RAW INPUT: [{"date":"2025-10-17","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T15:10:42+01:00] RAW INPUT: [{"date":"2025-10-21","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T15:11:00+01:00] RAW INPUT: [{"date":"2025-10-24","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T15:11:10+01:00] RAW INPUT: [{"date":"2025-12-02","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T15:11:57+01:00] RAW INPUT: [{"date":"2025-09-23","type":"PEP_SICK","duration":1}]
|
||||||
|
[2026-01-06T15:17:03+01:00] RAW INPUT: [{"date":"2025-09-10","type":"CENTRE","duration":1}]
|
||||||
|
[2026-01-06T15:26:35+01:00] RAW INPUT: [{"date":"2025-10-06","type":"PEP_SICK","duration":1},{"date":"2025-10-07","type":"PEP_SICK","duration":1},{"date":"2025-10-08","type":"PEP_SICK","duration":1}]
|
||||||
+1
-1
@@ -1,7 +1,7 @@
|
|||||||
<?php
|
<?php
|
||||||
header('Content-Type: application/json');
|
header('Content-Type: application/json');
|
||||||
|
|
||||||
require __DIR__ . '/../includes/db.php';
|
require __DIR__ . '/../../../../includes/db.php';
|
||||||
|
|
||||||
try {
|
try {
|
||||||
$stmt = $pdo->query("SELECT id, event_date AS date, event_type AS type, person_id, duration FROM pf_events ORDER BY event_date");
|
$stmt = $pdo->query("SELECT id, event_date AS date, event_type AS type, person_id, duration FROM pf_events ORDER BY event_date");
|
||||||
+1
-1
@@ -2,7 +2,7 @@
|
|||||||
// api/get-leaves.php
|
// api/get-leaves.php
|
||||||
header('Content-Type: application/json');
|
header('Content-Type: application/json');
|
||||||
|
|
||||||
require __DIR__ . '/../includes/db.php';
|
require __DIR__ . '/../../../../includes/db.php';
|
||||||
|
|
||||||
try {
|
try {
|
||||||
$stmt = $pdo->query("
|
$stmt = $pdo->query("
|
||||||
+1
-1
@@ -1,6 +1,6 @@
|
|||||||
<?php
|
<?php
|
||||||
header('Content-Type: application/json');
|
header('Content-Type: application/json');
|
||||||
require __DIR__ . '/../includes/db.php';
|
require __DIR__ . '/../../../../includes/db.php';
|
||||||
|
|
||||||
$input = json_decode(file_get_contents('php://input'), true);
|
$input = json_decode(file_get_contents('php://input'), true);
|
||||||
|
|
||||||
+1
-1
@@ -1,7 +1,7 @@
|
|||||||
<?php
|
<?php
|
||||||
// api/manage-leaf.php
|
// api/manage-leaf.php
|
||||||
header('Content-Type: application/json');
|
header('Content-Type: application/json');
|
||||||
require __DIR__ . '/../includes/db.php';
|
require __DIR__ . '/../../../../includes/db.php';
|
||||||
|
|
||||||
$input = json_decode(file_get_contents('php://input'), true);
|
$input = json_decode(file_get_contents('php://input'), true);
|
||||||
|
|
||||||
+10
-1
@@ -1,8 +1,17 @@
|
|||||||
<?php
|
<?php
|
||||||
header('Content-Type: application/json');
|
header('Content-Type: application/json');
|
||||||
require __DIR__ . '/../includes/db.php';
|
require __DIR__ . '/../../../../includes/db.php';
|
||||||
|
|
||||||
$eventsToSave = json_decode(file_get_contents('php://input'), true);
|
$eventsToSave = json_decode(file_get_contents('php://input'), true);
|
||||||
|
$rawInput = file_get_contents('php://input');
|
||||||
|
file_put_contents(
|
||||||
|
__DIR__ . '/events-debug.log',
|
||||||
|
"[" . date('c') . "] RAW INPUT: " . $rawInput . PHP_EOL,
|
||||||
|
FILE_APPEND
|
||||||
|
);
|
||||||
|
|
||||||
|
$eventsToSave = json_decode($rawInput, true);
|
||||||
|
|
||||||
|
|
||||||
if (empty($eventsToSave) || !is_array($eventsToSave)) {
|
if (empty($eventsToSave) || !is_array($eventsToSave)) {
|
||||||
http_response_code(400);
|
http_response_code(400);
|
||||||
+1
-1
@@ -2,7 +2,7 @@
|
|||||||
// api/save-leaves.php
|
// api/save-leaves.php
|
||||||
header('Content-Type: application/json');
|
header('Content-Type: application/json');
|
||||||
|
|
||||||
require __DIR__ . '/../includes/db.php';
|
require __DIR__ . '/../../../../includes/db.php';
|
||||||
|
|
||||||
$input = json_decode(file_get_contents('php://input'), true);
|
$input = json_decode(file_get_contents('php://input'), true);
|
||||||
|
|
||||||
Reference in New Issue
Block a user