refactor: combined duration (pages + minutes), has_annexes checkbox, remove Mo

- Remove Mo option from duration, keep only pages and minutes
- Redesign duration fieldset: separate Pages input + Durée h:m inputs, both can be set together
- Fix minutes input visibility: wider inputs (6ch), proper CSS layout
- Add has_annexes checkbox to fichiers fragment + DB column + controllers
- Display duration on admin backoffice recap page
- Display duration on public partage recap page
- Update public TFE page for new combined duration format
- Migration 041: add duration_pages, duration_minutes, has_annexes columns; migrate data; recreate views
This commit is contained in:
Pontoporeia
2026-07-03 15:58:10 +02:00
parent 42c4e78df6
commit 4fa57d592a
20 changed files with 335 additions and 173 deletions
+20 -16
View File
@@ -162,8 +162,9 @@ class ThesisCreateController
'exemplaire_baiu' => $data['exemplaireBaiu'],
'exemplaire_erg' => $data['exemplaireErg'],
'cc2r' => $data['cc2r'],
'duration_value' => $data['durationValue'],
'duration_unit' => $data['durationUnit'],
'duration_pages' => $data['durationPages'],
'duration_minutes' => $data['durationMins'],
'has_annexes' => $data['hasAnnexes'] ? 1 : 0,
]);
$identifier = $this->db->getThesisIdentifier($thesisId);
@@ -555,20 +556,22 @@ class ThesisCreateController
$exemplaireErg = !empty($post['exemplaire_erg']);
$cc2r = !empty($post['cc2r']);
// Duration: numeric value + unit (optional, admin-validated)
$validDurationUnits = ['pages', 'mo', 'durée'];
$durationValue = $post['duration_value'] ?? null;
$durationUnit = $post['duration_unit'] ?? 'pages';
if ($durationValue !== null && $durationValue !== '') {
$durationValue = filter_var($durationValue, FILTER_VALIDATE_FLOAT);
if ($durationValue === false || $durationValue <= 0) {
$durationValue = null; // ignore invalid
// Duration: separate pages (int) and time (h/m → total minutes)
$durationPages = null;
$durationPagesRaw = $post['duration_pages'] ?? null;
if ($durationPagesRaw !== null && $durationPagesRaw !== '') {
$durationPages = filter_var($durationPagesRaw, FILTER_VALIDATE_INT, ['options' => ['min_range' => 0]]);
if ($durationPages === false || $durationPages <= 0) {
$durationPages = null;
}
} else {
$durationValue = null;
}
if (!in_array($durationUnit, $validDurationUnits, true)) {
$durationUnit = 'pages';
$durationMins = null;
$durationMinsRaw = $post['duration_minutes'] ?? null;
if ($durationMinsRaw !== null && $durationMinsRaw !== '') {
$durationMins = filter_var($durationMinsRaw, FILTER_VALIDATE_INT, ['options' => ['min_range' => 0]]);
if ($durationMins === false || $durationMins <= 0) {
$durationMins = null;
}
}
// Annexes are optional — no validation required
@@ -601,8 +604,9 @@ class ThesisCreateController
'exemplaireBaiu',
'exemplaireErg',
'cc2r',
'durationValue',
'durationUnit'
'durationPages',
'durationMins',
'hasAnnexes'
);
}
+7 -6
View File
@@ -109,8 +109,8 @@ class ThesisEditController
$currentAccessTypeId = $rawRow['access_type_id'] ?? null;
$currentContextNote = $rawRow['context_note'] ?? '';
$currentContactVisible = $rawRow['contact_visible'] ?? '';
$currentDurationValue = $rawRow['duration_value'] ?? null;
$currentDurationUnit = $rawRow['duration_unit'] ?? 'pages';
$currentDurationPages = $rawRow['duration_pages'] ?? null;
$currentDurationMins = $rawRow['duration_minutes'] ?? null;
// Author contact info (from view)
$contactInterne = $thesis['contact_interne'] ?? '';
@@ -134,8 +134,8 @@ class ThesisEditController
'currentAccessTypeId' => $currentAccessTypeId,
'currentContextNote' => $currentContextNote,
'currentContactVisible' => $currentContactVisible,
'currentDurationValue' => $currentDurationValue,
'currentDurationUnit' => $currentDurationUnit,
'currentDurationPages' => $currentDurationPages,
'currentDurationMins' => $currentDurationMins,
'contactInterne' => $contactInterne,
'contactPublic' => $contactPublic,
'currentRaw' => $rawRow,
@@ -223,8 +223,9 @@ class ThesisEditController
'exemplaire_erg' => !empty($post['exemplaire_erg']),
'cc2r' => !empty($post['cc2r']),
'license_custom' => trim($post['license_custom'] ?? ''),
'duration_value' => isset($post['duration_value']) && $post['duration_value'] !== '' ? (float)$post['duration_value'] : null,
'duration_unit' => !empty($post['duration_unit']) ? $post['duration_unit'] : 'pages',
'duration_pages' => (isset($post['duration_pages']) && $post['duration_pages'] !== '') ? (int)$post['duration_pages'] : null,
'duration_minutes' => (isset($post['duration_minutes']) && $post['duration_minutes'] !== '') ? (int)$post['duration_minutes'] : null,
'has_annexes' => !empty($post['has_annexes']) ? 1 : 0,
];
// Regenerate identifier if year changed or if identifier prefix doesn't match year
$oldThesis = $this->db->getThesis($thesisId);