From bd1f084862461f05d5d2b5a6391917046a311ebf Mon Sep 17 00:00:00 2001 From: kdeterme Date: Sat, 8 Aug 2026 15:46:33 +0200 Subject: [PATCH] feat: add "concepts" help guide and introduce expandable help panel view --- streetup/common/help_docs/fr/concepts.md | 79 +++++++ streetup/common/help_docs/fr/prise_en_main.md | 45 ++-- streetup/common/help_docs/nl/concepts.md | 79 +++++++ streetup/common/help_docs/nl/prise_en_main.md | 45 ++-- streetup/common/static/common/help_panel.css | 18 ++ streetup/common/static/common/help_panel.js | 159 ++++++++++--- .../common/components/help_panel.html | 215 +++++++++++------- streetup/common/views.py | 2 +- streetup/templates/base.html | 80 +++---- 9 files changed, 533 insertions(+), 189 deletions(-) create mode 100644 streetup/common/help_docs/fr/concepts.md create mode 100644 streetup/common/help_docs/nl/concepts.md diff --git a/streetup/common/help_docs/fr/concepts.md b/streetup/common/help_docs/fr/concepts.md new file mode 100644 index 0000000..11ec9e2 --- /dev/null +++ b/streetup/common/help_docs/fr/concepts.md @@ -0,0 +1,79 @@ +# Concepts clés de StreetUp + +StreetUp organise la gestion du patrimoine et des opérations terrain autour de plusieurs notions fondamentales. Comprendre leurs rôles et leurs distinctions permet d'optimiser l'utilisation de la plateforme. + +--- + +## 1. Vue d'ensemble du cycle de vie + +L'écosystème StreetUp s'articule autour du cycle suivant : +1. **Patrimoine** (`Asset`) : Les équipements physiques présents sur le terrain. +2. **Constat & Diagnostic** (`Observation` / `Inspection`) : Ce que l'on signale à chaud ou ce que l'on contrôle de manière formelle. +3. **Travaux & Maintenance** (`Intervention` / `Projet`) : L'action corrective ou préventive menée sur le terrain. +4. **Recette & Conformité** (`Contrôle`) : La vérification formelle de la bonne réalisation des travaux. +5. **Cadre financier & Logistique** (`Commande` / `Stock` / `Équipe`) : Les marchés, pièces et ressources mobilisés. + +--- + +## 2. Définitions et distinctions des éléments clés + +### 📍 Asset (Équipement / Patrimoine) +- **Définition** : Élément physique géolocalisé du domaine public (ex: panneau de signalisation, candélabre, potelet, ouvrage GIEP, emplacement vélo). +- **Rôle** : Servir de référence centrale pour l'historique de tous les constats, interventions et contrôles associés. + +### 👁️ Observation (Signalement spontané) +- **Définition** : Constat rapide "à chaud" ou alerte spontanée sur le terrain. +- **Acteurs** : Agents de voirie, observateurs, citoyens. +- **Exemple** : *"Signalement d'un dépôt sauvage ou d'un potelet plié dans une rue."* +- **Distinction** : Une observation est un événement ponctuel et spontané, contrairement à une inspection qui est formalisée. + +### 🔍 Inspection (Évaluation de conformité / Diagnostic) +- **Définition** : Évaluation structurée de l'état ou de la conformité d'une cible (Asset, Localisation ou Intervention) à un instant T. +- **Acteurs** : Observers, prestataires techniques, experts. +- **Exemple** : *"Contrôle visuel de l'état d'un ouvrage de drainage ou mesure électrique d'un candélabre."* +- **Distinction** : Une inspection ne modifie pas directement l'équipement sur le terrain ; elle produit un diagnostic (conforme / non conforme / endommagé) qui peut déclencher une intervention. + +### 🛠️ Intervention (Action de travaux / Maintenance) +- **Définition** : Action de terrain corrective ou préventive visant à réparer, entretenir ou remplacer un équipement. +- **Acteurs** : Régie interne, prestataires de travaux. +- **Exemple** : *"Réparation d'un nid de poule", "Remplacement d'une lanterne de signalisation".* +- **Distinction** : L'intervention est l'action physique de travaux, alors que l'inspection est le diagnostic et le contrôle est la vérification. + +### ✅ Contrôle (Réception & Recette des travaux) +- **Définition** : Vérification formelle de l'exécution des travaux visant à valider la qualité et à prononcer la réception d'un chantier. +- **Acteurs** : Contrôleurs travaux, gestionnaires de contrats. +- **Exemple** : *"Procès-verbal de réception des réfections de chaussée d'un marché."* +- **Distinction** : Le contrôle intervient **après** la réalisation des travaux pour valider leur conformité contractuelle et autoriser la facturation. + +### 📁 Projet (Chantier d'envergure / Regroupement) +- **Définition** : Regroupement thématique, géographique ou temporel de plusieurs interventions. +- **Exemple** : *"Réaménagement de l'avenue de la Gare (comprenant 15 interventions de voirie, signalisation et éclairage)".* + +### 💶 Commande (Cadre budgétaire & Marché) +- **Définition** : Ordre de service ou bon de commande rattaché à un marché/contrat qui encadre financièrement les travaux. + +--- + +## 3. Tableau comparatif synthétique + +| Concept | Nature | Déclencheur | Objectif principal | +| :--- | :--- | :--- | :--- | +| **Asset** | Patrimoine physique | Création / Inventaire | Identifier l'équipement géolocalisé | +| **Observation** | Signalement à chaud | Spontané | Alerter sur un dysfonctionnement ou une anomalie | +| **Inspection** | Diagnostic formalisé | Planifié ou terrain | Évaluer l'état de conformité d'une cible à un instant T | +| **Intervention** | Action de travaux | Suite à alerte / programme | Réparer, remplacer ou entretenir l'équipement | +| **Contrôle** | Vérification qualité | Post-travaux | Valider la conformité de l'intervention et procéder à la réception | +| **Projet** | Regroupement de travaux | Cadrage opérationnel | Piloter un chantier comportant plusieurs interventions | +| **Commande** | Cadrage financier | Cadrage contractuel | Gérer les bons de commande et budgets des marchés | + +--- + +## 4. Relations particulières : Inspection vs Intervention vs Contrôle + +### Dualité entre `Inspection` et `Intervention` +1. **L'Inspection d'une Intervention (Suivi qualité)** : Une inspection peut cibler une intervention réalisée (ex: vérification à J+30 de la tenue d'une réparation). +2. **L'Intervention comme Cadre de Mission d'Inspections** : Une intervention de type *"mission d'inspection"* sert de conteneur administratif et financier (bon de commande, prestataire assigné) pour réaliser une campagne de $N$ inspections sur le terrain (ex: campagne annuelle de contrôle des ouvrages GIEP). + +### Différence entre `Inspection` et `Contrôle` +- **L'Inspection** évalue la conformité d'un **équipement (Asset)** ou d'une **zone (Location)**, ou assure un suivi technique. +- **Le Contrôle** évalue la réalisation de la **prestation de travaux (Intervention)** en vue de sa validation administrative et financière par le gestionnaire. diff --git a/streetup/common/help_docs/fr/prise_en_main.md b/streetup/common/help_docs/fr/prise_en_main.md index 5bc658b..80a76ec 100644 --- a/streetup/common/help_docs/fr/prise_en_main.md +++ b/streetup/common/help_docs/fr/prise_en_main.md @@ -1,27 +1,40 @@ -# Prise en main de StreetUp +# Prise en main de StreetUp Bienvenue dans StreetUp ! Ce guide rapide va vous présenter les bases de la navigation et de l'utilisation de l'application. -## 1. La barre de navigation principale (Header) +## 1. La barre de navigation principale (Header) En haut de votre écran, vous trouverez la barre d'outils contenant : - L'accès à vos informations de compte. - Un sélecteur de vue (si vous avez accès à plusieurs portails). -- Le centre de notifications () pour suivre les discussions et alertes. -- Le sélecteur de langue () pour basculer entre le français et le néerlandais. -- Le bouton d'aide () qui ouvre ce panneau. +- Le centre de notifications () pour suivre les discussions et alertes. +- Le sélecteur de langue () pour basculer entre le français et le néerlandais. +- Le bouton d'aide () qui ouvre ce panneau. -## 2. Le menu latéral (Sidebar) -À gauche de l'écran (ou via le menu repliable sur mobile), vous pouvez naviguer vers : -- **Accueil** : Votre tableau de bord personnalisé avec vos compteurs d'interventions et de signalements. -- **Assets** : L'inventaire de vos équipements de voirie sur carte et en tableau. -- **Observations** : Vos constats et inspections sur le terrain. -- **Interventions** : Le suivi des chantiers et travaux de maintenance corrective ou préventive. -- **Projets** : La planification des travaux d'envergure. +## 2. Le menu latéral (Sidebar) +À gauche de l'écran (ou via le menu repliable sur mobile), le menu principal est structuré en 5 blocs thématiques pour suivre le cycle de vie de votre patrimoine et de vos opérations : -## 3. Dispositions d'affichage +- Accueil : Votre tableau de bord personnalisé et vos synthèses d'activité. +- Patrimoine & Diagnostics : + - Assets : Inventaire cartographique et tabulaire de tous vos équipements. + - Observations : Signalements et constats rapides sur le terrain. + - Inspections : Visites de contrôle structurées et diagnostics de l'état des équipements. +- Gestion & Exécution des travaux : + - Commandes : Gestion des marchés, ordres de service et cadrages budgétaires. + - Projets : Planification et regroupement des travaux d'envergure. + - Interventions : Suivi des travaux de maintenance corrective ou préventive. + - Contrôles : Vérification qualité et recette des travaux réalisés. +- Planification & Ressources : + - Calendrier : Vue temporelle et agenda des interventions et chantiers. + - Équipes : Organisation et affectation des équipes d'intervention. +- Logistique & Matériel : + - Entrepôts : Gestion de vos lieux de stockage de matériel. + - Flux de stock : Mouvements, entrées/sorties et traçabilité des pièces. + - Achats : Demandes et commandes de matériel et fournitures. + +## 3. Dispositions d'affichage Sur la plupart des pages (Assets, Interventions), vous pouvez choisir d'afficher : -- La **carte** seule (). -- Le **tableau** des données seul (). -- Les **deux** côte à côte (, par défaut). +- La **carte** seule (). +- Le **tableau** des données seul (). +- Les **deux** côte à côte (, par défaut). Ces boutons (situés en haut à droite des pages concernées) vous permettent de masquer la carte ou le tableau pour maximiser votre espace de travail. Vos choix de disposition sont automatiquement sauvegardés pour vos prochaines visites. diff --git a/streetup/common/help_docs/nl/concepts.md b/streetup/common/help_docs/nl/concepts.md new file mode 100644 index 0000000..7bb7a50 --- /dev/null +++ b/streetup/common/help_docs/nl/concepts.md @@ -0,0 +1,79 @@ +# Sleutelbegrippen in StreetUp + +StreetUp organiseert het beheer van de openbare ruimte en terreinoperaties rond verschillende fundamentele begrippen. Het begrijpen van hun rol en onderlinge verschillen helpt om het platform optimaal te gebruiken. + +--- + +## 1. Overzicht van de levenscyclus + +Het StreetUp-ecosysteem is opgebouwd rond de volgende cyclus: +1. **Patrimonium** (`Asset`): Fysieke uitrustingen op het terrein. +2. **Vaststelling & Diagnose** (`Observatie` / `Inspectie`): Meldingen ter plaatse of formele controles. +3. **Werken & Onderhoud** (`Interventie` / `Project`): Correctieve of preventieve acties op het terrein. +4. **Oplevering & Conformiteit** (`Controle`): Formele verificatie van de correcte uitvoering van de werken. +5. **Financieel & Logistiek kader** (`Bestelling` / `Voorraad` / `Team`): Opdrachten, wisselstukken en ingezette middelen. + +--- + +## 2. Definities en verschillen tussen sleutelelementen + +### 📍 Asset (Uitrusting / Patrimonium) +- **Definitie**: Geolokaliseerd fysiek element van het openbaar domein (bv. verkeersbord, verlichtingspaal, fietsenstalling). +- **Rol**: Centraal referentiepunt voor de geschiedenis van alle geassocieerde vaststellingen, interventies en controles. + +### 👁️ Observatie (Snelle melding) +- **Definitie**: Snelle vaststelling of spontane melding op het terrein. +- **Actoren**: Wegopzichters, waarnemers, burgers. +- **Voorbeeld**: *"Melding van sluikstort of een gebogen paaltje in een straat."* +- **Verschil**: Een observatie is spontaan en eenmalig, in tegenstelling tot een gestructureerde inspectie. + +### 🔍 Inspectie (Conformiteitsdiagnose) +- **Definitie**: Gestructureerde evaluatie van de staat of conformiteit van een doel (Asset, Locatie of Interventie) op een tijdstip T. +- **Actoren**: Inspecteurs, technische dienstverleners, experts. +- **Voorbeeld**: *"Visuele controle van de staat van een drainagewerk of elektrische meting van een verlichtingspaal."* +- **Verschil**: Een inspectie wijzigt de uitrusting niet rechtstreeks, maar levert een diagnose op (conform / niet conform / beschadigd) die een interventie kan uitlokken. + +### 🛠️ Interventie (Werken / Onderhoud) +- **Definitie**: Actie op het terrein om uitrustingen te herstellen, te onderhouden of te vervangen. +- **Actoren**: Interne regie, aannemers. +- **Voorbeeld**: *"Herstelling van een put in het wegdek", "Vervanging van een seinlamp".* +- **Verschil**: De interventie is de fysieke uitvoering van de werken, terwijl de inspectie de diagnose is en de controle de verificatie achteraf. + +### ✅ Controle (Oplevering van werken) +- **Definitie**: Formele verificatie van de uitvoering van de werken om de kwaliteit te valideren en de oplevering van een werf te bevestigen. +- **Actoren**: Werfcontrollers, contractmanagers. +- **Voorbeeld**: *"Proces-verbaal van oplevering van de wegeniswerken van een opdracht."* +- **Verschil**: De controle vindt plaats **na** de uitvoering van de werken om hun contractuele conformiteit te valideren. + +### 📁 Project (Grote werf / Groepering) +- **Definitie**: Thematische, geografische of temporele groepering van meerdere interventies. +- **Voorbeeld**: *"Heraanleg van de Stationslaan (bestaande uit 15 interventies voor wegenis, signalisatie en verlichting)".* + +### 💶 Bestelling (Budgettair kader & Opdracht) +- **Definitie**: Dienstorder of bestelbon gekoppeld aan een contract/opdracht die de werken financieel omkaderd. + +--- + +## 3. Vergelijkende samenvattingstabel + +| Begrip | Aard | Triggermoment | Hoofddoel | +| :--- | :--- | :--- | :--- | +| **Asset** | Fysiek patrimonium | Aanmaak / Inventaris | Geolokaliseerde uitrusting identificeren | +| **Observatie** | Snelle melding | Spontaan | Waarschuwen voor een defect of anomalie | +| **Inspectie** | Formele diagnose | Gepland of terrein | Conformiteitsstaat evalueren op tijdstip T | +| **Interventie** | Uitvoering van werken | Na melding / programma | Herstellen, vervangen of onderhouden | +| **Controle** | Kwaliteitsverificatie | Na de werken | Conformiteit van de interventie valideren en opleveren | +| **Project** | Werfgroepering | Operationeel kader | Werf beheren met meerdere interventies | +| **Bestelling** | Financieel kader | Contractueel kader | Bestelbonnen en budgetten van opdrachten beheren | + +--- + +## 4. Bijzondere relaties: Inspectie vs Interventie vs Controle + +### Dualiteit tussen `Inspectie` en `Interventie` +1. **De Inspectie van een Interventie (Kwaliteitsopvolging)**: Een inspectie kan gericht zijn op een uitgevoerde interventie (bv. controle na 30 dagen van de herstelling). +2. **De Interventie als Kader voor Inspectieopdrachten**: Een interventie van het type *"inspectieopdracht"* dient als administratieve en financiële container voor een inspectiecampagne op het terrein. + +### Verschil tussen `Inspectie` en `Controle` +- **De Inspectie** evalueert de conformiteit van een **uitrusting (Asset)** of **zone (Locatie)**. +- **De Controle** evalueert de uitvoering van de **geleverde werken (Interventie)** met het oog op de administratieve en financiële goedkeuring door de beheerder. diff --git a/streetup/common/help_docs/nl/prise_en_main.md b/streetup/common/help_docs/nl/prise_en_main.md index beb8d6d..15004db 100644 --- a/streetup/common/help_docs/nl/prise_en_main.md +++ b/streetup/common/help_docs/nl/prise_en_main.md @@ -1,27 +1,40 @@ -# Aan de slag met StreetUp +# Aan de slag met StreetUp Welkom bij StreetUp! Deze snelle handleiding toont u de basisprincipes van navigatie en gebruik van de applicatie. -## 1. De hoofdnavigatiebalk (Header) +## 1. De hoofdnavigatiebalk (Header) Bovenaan uw scherm vindt u de knoppenbalk met: - Toegang tot uw accountgegevens. - Een weergaveschakelaar (als u toegang heeft tot meerdere portalen). -- Het notificatiecentrum () om discussies en waarschuwingen te volgen. -- De taalkeuze () om te schakelen tussen Frans en Nederlands. -- De helpknop () die dit paneel opent. +- Het notificatiecentrum () om discussies en waarschuwingen te volgen. +- De taalkeuze () om te schakelen tussen Frans en Nederlands. +- De helpknop () die dit paneel opent. -## 2. Het zijmenu (Sidebar) -Aan de linkerkant van het scherm (of via het inklapbare menu op mobiel) kunt u navigeren naar: -- **Home**: Uw gepersonaliseerde dashboard met tellers voor interventies en meldingen. -- **Assets**: De inventaris van uw weginfrastructuur op kaart en in tabelvorm. -- **Observaties**: Uw vaststellingen en inspecties op het terrein. -- **Interventies**: De opvolging van werven en onderhoudswerken (correctief of preventief). -- **Projecten**: De planning van grotere werken. +## 2. Het zijmenu (Sidebar) +Aan de linkerkant van het scherm (of via het inklapbare menu op mobiel) is het hoofdmenu gestructureerd in 5 thematische blokken die de levenscyclus van uw patrimonium en uw operaties volgen: -## 3. Weergave-indelingen +- Home: Uw gepersonaliseerde dashboard en activiteitsoverzichten. +- Patrimonium & Diagnoses: + - Assets: Inventaris op kaart en in tabelvorm van al uw uitrustingen. + - Observaties: Snelle meldingen en vaststellingen op het terrein. + - Inspecties: Gestructureerde controlebezoeken en diagnoses van de staat van de uitrustingen. +- Beheer & Uitvoering van de werken: + - Bestellingen: Beheer van opdrachten, dienstorders en budgettair kader. + - Projecten: Planning en groepering van grotere werken. + - Interventies: Opvolging van onderhoudswerken (correctief of preventief). + - Controles: Kwaliteitsverificatie en oplevering van de uitgevoerde werken. +- Planning & Middelen: + - Kalender: Tijdsweergave en agenda van interventies en werven. + - Teams: Organisatie en toewijzing van interventieteams. +- Logistiek & Materiaal: + - Magazijnen: Beheer van uw opslaglocaties voor materiaal. + - Voorraadstromen: Bewegingen, in-/uitgangen en traceerbaarheid van onderdelen. + - Aankopen: Aanvragen en bestellingen van materiaal en benodigdheden. + +## 3. Weergave-indelingen Op de meeste pagina's (Assets, Interventies) kunt u kiezen om weer te geven: -- Alleen de **kaart** (). -- Alleen de **tabel** met gegevens (). -- **Beide** naast elkaar (, standaard). +- Alleen de **kaart** (). +- Alleen de **tabel** met gegevens (). +- **Beide** naast elkaar (, par défaut). Met deze knoppen (bovenaan rechts op de betreffende pagina's) kunt u de kaart of de tabel verbergen om uw werkruimte te maximaliseren. Uw voorkeuren voor de indeling worden automatisch opgeslagen voor uw volgende bezoeken. diff --git a/streetup/common/static/common/help_panel.css b/streetup/common/static/common/help_panel.css index bde922a..4951d79 100644 --- a/streetup/common/static/common/help_panel.css +++ b/streetup/common/static/common/help_panel.css @@ -282,3 +282,21 @@ width: 2.5rem; height: 2.5rem; } + +/* Styles for Help Content inside Large Format Modal */ +#help-content-container.in-modal .help-guide-list { + display: grid; + grid-template-columns: repeat(auto-fill, minmax(320px, 1fr)); + gap: 1.25rem; +} + +#help-content-container.in-modal .help-markdown-content { + max-width: 960px; + margin: 0 auto; + padding: 0.5rem 1rem; +} + +#help-content-container.in-modal .help-search-wrapper { + max-width: 500px; +} + diff --git a/streetup/common/static/common/help_panel.js b/streetup/common/static/common/help_panel.js index 6c2e8b4..9af164c 100644 --- a/streetup/common/static/common/help_panel.js +++ b/streetup/common/static/common/help_panel.js @@ -1,4 +1,4 @@ -/* Help Panel Interaction Javascript */ +/* Help Panel & Modal Interaction Javascript */ document.addEventListener('DOMContentLoaded', () => { // DOM Elements @@ -6,7 +6,14 @@ document.addEventListener('DOMContentLoaded', () => { const panel = document.getElementById('help-sidebar-panel'); const backdrop = document.getElementById('help-panel-backdrop'); const closeBtn = document.getElementById('helpPanelClose'); + const expandBtn = document.getElementById('helpExpandBtn'); + const modalEl = document.getElementById('helpLargeModal'); + const modalBody = document.getElementById('helpModalBody'); + const sidebarBody = document.getElementById('help-sidebar-body'); + const contentContainer = document.getElementById('help-content-container'); + const modalSwitchToSidebarBtn = document.getElementById('helpModalSwitchToSidebarBtn'); + const indexView = document.getElementById('help-index-view'); const detailView = document.getElementById('help-detail-view'); const backBtn = document.getElementById('help-back-btn'); @@ -20,42 +27,128 @@ document.addEventListener('DOMContentLoaded', () => { return; } - // Toggle Drawer Open/Close - function openHelpPanel() { + let bsHelpModal = null; + if (modalEl && window.bootstrap && window.bootstrap.Modal) { + bsHelpModal = new bootstrap.Modal(modalEl); + } + + // Persistent display mode ('sidebar' | 'modal') saved in localStorage + function getDisplayMode() { + return localStorage.getItem('help_display_mode') || 'sidebar'; + } + + function setDisplayMode(mode) { + localStorage.setItem('help_display_mode', mode); + } + + // Attach content container to target parent element (sidebar or modal) + function attachContentToTarget(targetMode) { + if (!contentContainer) return; + + if (targetMode === 'modal' && modalBody) { + if (contentContainer.parentElement !== modalBody) { + modalBody.appendChild(contentContainer); + } + contentContainer.classList.add('in-modal'); + } else if (sidebarBody) { + if (contentContainer.parentElement !== sidebarBody) { + sidebarBody.appendChild(contentContainer); + } + contentContainer.classList.remove('in-modal'); + } + } + + // Open Help according to display mode + function openHelp(requestedMode) { + const mode = requestedMode || getDisplayMode(); + + if (mode === 'modal' && bsHelpModal) { + closeSidebarPanelSilent(); + attachContentToTarget('modal'); + bsHelpModal.show(); + sessionStorage.setItem('helpPanelOpen', 'true'); + sessionStorage.setItem('helpPanelDisplayMode', 'modal'); + } else { + if (bsHelpModal) bsHelpModal.hide(); + attachContentToTarget('sidebar'); + openSidebarPanel(); + } + } + + function openSidebarPanel() { panel.classList.add('open'); backdrop.classList.add('show'); sessionStorage.setItem('helpPanelOpen', 'true'); + sessionStorage.setItem('helpPanelDisplayMode', 'sidebar'); + } + + function closeSidebarPanelSilent() { + panel.classList.remove('open'); + backdrop.classList.remove('show'); } function closeHelpPanel() { - panel.classList.remove('open'); - backdrop.classList.remove('show'); + closeSidebarPanelSilent(); + if (bsHelpModal) bsHelpModal.hide(); sessionStorage.setItem('helpPanelOpen', 'false'); sessionStorage.removeItem('helpPanelDoc'); - // Reset to index view when closing setTimeout(() => { showIndexView(); if (searchInput) { searchInput.value = ''; filterGuides(''); } - }, 350); // wait for transition + }, 350); } + // Toggle help on trigger click trigger.addEventListener('click', (e) => { e.preventDefault(); - if (panel.classList.contains('open')) { + const isModalVisible = modalEl && modalEl.classList.contains('show'); + const isSidebarOpen = panel.classList.contains('open'); + + if (isModalVisible) { + if (bsHelpModal) bsHelpModal.hide(); + sessionStorage.setItem('helpPanelOpen', 'false'); + } else if (isSidebarOpen) { closeHelpPanel(); } else { - openHelpPanel(); + openHelp(); } }); + // Expand button (Sidebar -> Modal) + if (expandBtn) { + expandBtn.addEventListener('click', (e) => { + e.preventDefault(); + setDisplayMode('modal'); + openHelp('modal'); + }); + } + + // Switch to sidebar button (Modal -> Sidebar) + if (modalSwitchToSidebarBtn) { + modalSwitchToSidebarBtn.addEventListener('click', (e) => { + e.preventDefault(); + setDisplayMode('sidebar'); + openHelp('sidebar'); + }); + } + closeBtn.addEventListener('click', closeHelpPanel); backdrop.addEventListener('click', closeHelpPanel); - // Escape Key to Close + // Track modal close via bootstrap backdrop / ESC + if (modalEl) { + modalEl.addEventListener('hidden.bs.modal', () => { + if (sessionStorage.getItem('helpPanelDisplayMode') === 'modal') { + sessionStorage.setItem('helpPanelOpen', 'false'); + } + }); + } + + // Escape Key to Close Sidebar document.addEventListener('keydown', (e) => { if (e.key === 'Escape' && panel.classList.contains('open')) { closeHelpPanel(); @@ -93,9 +186,9 @@ document.addEventListener('DOMContentLoaded', () => { }); if (visibleCount === 0) { - noResults.classList.remove('d-none'); + if (noResults) noResults.classList.remove('d-none'); } else { - noResults.classList.add('d-none'); + if (noResults) noResults.classList.add('d-none'); } } @@ -127,7 +220,8 @@ document.addEventListener('DOMContentLoaded', () => { function showDetailView() { indexView.classList.add('d-none'); detailView.classList.remove('d-none'); - detailView.scrollTop = 0; + if (detailView) detailView.scrollTop = 0; + if (modalBody) modalBody.scrollTop = 0; } // Dynamic AJAX loading @@ -135,7 +229,6 @@ document.addEventListener('DOMContentLoaded', () => { showDetailView(); sessionStorage.setItem('helpPanelDoc', docName); - // Show loading spinner const loadingText = panel.getAttribute('data-loading-text') || 'Chargement...'; detailContent.innerHTML = `
@@ -181,24 +274,30 @@ document.addEventListener('DOMContentLoaded', () => { // Restore state from sessionStorage on page load const isHelpOpen = sessionStorage.getItem('helpPanelOpen') === 'true'; const activeDocName = sessionStorage.getItem('helpPanelDoc'); + const storedDisplayMode = sessionStorage.getItem('helpPanelDisplayMode') || getDisplayMode(); if (isHelpOpen) { - // Temporarily disable transition to prevent visible flicker - const originalPanelTransition = panel.style.transition; - const originalBackdropTransition = backdrop.style.transition; - panel.style.transition = 'none'; - backdrop.style.transition = 'none'; - - openHelpPanel(); - - if (activeDocName) { - loadHelpDocument(activeDocName); + if (storedDisplayMode === 'modal') { + openHelp('modal'); + if (activeDocName) { + loadHelpDocument(activeDocName); + } + } else { + const originalPanelTransition = panel.style.transition; + const originalBackdropTransition = backdrop.style.transition; + panel.style.transition = 'none'; + backdrop.style.transition = 'none'; + + openHelp('sidebar'); + + if (activeDocName) { + loadHelpDocument(activeDocName); + } + + setTimeout(() => { + panel.style.transition = originalPanelTransition; + backdrop.style.transition = originalBackdropTransition; + }, 50); } - - // Restore transition after browser renders the initial open state - setTimeout(() => { - panel.style.transition = originalPanelTransition; - backdrop.style.transition = originalBackdropTransition; - }, 50); } }); diff --git a/streetup/common/templates/common/components/help_panel.html b/streetup/common/templates/common/components/help_panel.html index c6e5358..18c7b75 100644 --- a/streetup/common/templates/common/components/help_panel.html +++ b/streetup/common/templates/common/components/help_panel.html @@ -15,104 +15,145 @@ {% translate "Centre d'aide" %} - +
+ + +
-
+
- -
- -
- - -
- - -
+
+ +
+ +
+ + +
- - -
- - -
- -
- - - -
- - -
- -
- - - -
- - -
- -
+ +
+ + + +
+ + +
+ +
+ + + +
+ + +
+ +
+ + + +
+ + +
+ +
+ + + +
+ + +
+ +
- - {% if user.config.can_approve_any_intervention %} - -
- - + + {% if user.config.can_approve_any_intervention %} + +
+ + +
+ +
+ {% endif %} + + + {% if user.config|has_any_role:"admin,manager,controller,external_manager,top_manager" or user.is_superuser %} + +
+ + +
+ +
+ {% endif %} + + + {% if user.config|has_any_role:"admin,manager,controller,external_manager,top_manager" or user.is_superuser %} + +
+ + +
+ +
+ {% endif %} + + +
+ + {% translate "Aucun guide ne correspond à votre recherche." %}
- - - {% endif %} - - - {% if user.config|has_any_role:"admin,manager,controller,external_manager,top_manager" or user.is_superuser %} - -
- - -
- -
- {% endif %} - - - {% if user.config|has_any_role:"admin,manager,controller,external_manager,top_manager" or user.is_superuser %} - -
- - -
- -
- {% endif %} - - -
- - {% translate "Aucun guide ne correspond à votre recherche." %}
-
- - -
-
- -
- -
+ +
+
+ +
+ + +
+
+ + + diff --git a/streetup/common/views.py b/streetup/common/views.py index 5aef4f3..c52ef4c 100644 --- a/streetup/common/views.py +++ b/streetup/common/views.py @@ -545,7 +545,7 @@ def get_help_document(request, doc_name): from django.utils import translation from django.http import HttpResponseForbidden - ALLOWED_DOCS = ['prise_en_main', 'assets', 'approuver_interventions', 'gerer_projets', 'statuts_intervention', 'creer_controle'] + ALLOWED_DOCS = ['prise_en_main', 'concepts', 'assets', 'approuver_interventions', 'gerer_projets', 'statuts_intervention', 'creer_controle'] if doc_name not in ALLOWED_DOCS: return JsonResponse({'error': _('Document non trouvé')}, status=404) diff --git a/streetup/templates/base.html b/streetup/templates/base.html index 3313f5d..87c4be6 100644 --- a/streetup/templates/base.html +++ b/streetup/templates/base.html @@ -339,38 +339,23 @@