wiki/c-work/1-plan/2026-06-modal-consolidation.md

108 lines
4.6 KiB
Markdown

<!-- status: plan -->
<!-- started: 2026-06-10 -->
<!-- component: ui-nyla -->
# Modal-Konsolidierung
## Beschreibung und Kontext
Aktuell gibt es 3 verschiedene Modal-Implementierungen im System. Das ist nicht wartbar und fuehrt zu inkonsistentem Verhalten (Backdrop, ESC-Handling, Focus-Trap, Accessibility).
## Ist-Zustand
### 3 Modal-Patterns
| Pattern | Komponente | Nutzung |
|---------|-----------|---------|
| `useConfirm()` Hook | `ConfirmDialog` | 6 Seiten (Bestaetigungs-Dialoge) |
| `usePrompt()` Hook | `PromptDialog` | 4 Seiten (Text-Eingabe-Dialoge) |
| `<Modal>` Komponente | `UiComponents/Modal` | 1 Seite (EnterpriseDialog) |
| `div.modalOverlay` + CSS | Per Seite dupliziert | ~25 Seiten |
### modalOverlay mit FormGeneratorForm (~15 Seiten)
Overlay-Container ist per CSS-Modul dupliziert (`Admin.module.css`, `TrusteeViews.module.css`, etc.), Inhalt ist `FormGeneratorForm` — halbwegs standardisiert.
Betroffene Seiten:
- Admin: AdminUsersPage, AdminUserMandatesPage, AdminMandatesPage, AdminMandateRolesPage, AdminInvitationsPage, AdminFeatureRolesPage, AdminFeatureInstanceUsersPage, AdminFeatureAccessPage
- Trustee: TrusteeDataTab, TrusteeDocumentsView, TrusteePositionsView, TrusteePositionDocumentsView
- Basedata: ConnectionsPage, FilesPage, PromptsPage
- Feature: CommcoachSettingsView, RealEstateParcelsView, RealEstateProjectsView
### modalOverlay mit Custom-Inhalt (~10 Seiten)
Diese Seiten haben Modale ohne FormGeneratorForm:
| Seite | Inhalt |
|-------|--------|
| RunsTab | Run-Tracing Detail-Ansicht |
| NeutralizationView | SharePoint Ordner-Browser |
| InstanceDetailModal | Multi-Tab-Modal (UiComponents/Tabs) mit verschachtelten Sub-Modalen |
| AdminMandateRolePermissionsPage | Duplikate-Cleanup mit Custom-Tabellen |
| AdminFeatureAccessPage | Feature-Button-Grid zur Auswahl |
| AdminInvitationsPage | URL-Anzeige mit Copy-Button |
| AdminFeatureRolesPage | AccessRulesEditor (Berechtigungen) |
| FeatureInstanceWizard | 3-Schritt-Wizard im Modal |
| ComplianceAuditPage | Content-View (Input/Output) |
| TeamsbotModulesView | Inline confirmDialog (nicht Hook) |
| CommcoachModulesView | Inline confirmDialog (nicht Hook) |
| Settings | ProfileEditModal (mit FormGeneratorForm) |
## Ziel
- **Ein** Modal-Container fuer alle Anwendungsfaelle
- Backdrop, ESC, Focus-Trap, ARIA (`role="dialog"`, `aria-modal`) konsistent
- FormGeneratorForm-Modale: Zero-Boilerplate (kein manueller Overlay-Code auf der Seite)
- Custom-Modale: Gleicher Container, freier Inhalt
- `useConfirm` und `usePrompt` als spezialisierte Wrapper bleiben (sind bereits OK)
## Entscheidungen
| Datum | Entscheidung | Begruendung |
|-------|-------------|------------|
| 2026-06-10 | Separater Plan, nicht Teil des Layout-Refactoring | Modale sind Overlays, keine Seitenregionen. Unabhaengig loesbar. |
## Vorgeschlagene Architektur
### Bestehende `<Modal>` Komponente erweitern
`UiComponents/Modal/Modal.tsx` existiert bereits, wird aber nur von `EnterpriseDialog.tsx` genutzt. Diese Komponente wird zum Standard.
### Stufen
| Stufe | Aktion |
|-------|--------|
| 1 | `<Modal>` Komponente pruefen: hat sie Backdrop, ESC, Focus-Trap, ARIA, Groessen-Varianten? Fehlende Features ergaenzen. |
| 2 | `useFormModal()` Hook erstellen: Oeffnet `<Modal>` mit `<FormGeneratorForm>` — ersetzt 15 Seiten mit modalOverlay+FormGeneratorForm |
| 3 | Custom-Modale auf `<Modal>` migrieren (10 Seiten) |
| 4 | `modalOverlay`-CSS aus allen CSS-Modulen entfernen |
| 5 | `TeamsbotModulesView` und `CommcoachModulesView` auf `useConfirm()` Hook umstellen |
## Betroffene Module
- `components/UiComponents/Modal/Modal.tsx` + `.module.css` — erweitern
- Neuer Hook: `hooks/useFormModal.ts`
- ~25 Seiten: modalOverlay entfernen, durch `<Modal>` oder `useFormModal()` ersetzen
- CSS-Module: `Admin.module.css`, `TrusteeViews.module.css`, etc. — modalOverlay-Klassen entfernen
## Akzeptanzkriterien
| # | Kriterium | Prio |
|---|-----------|------|
| 1 | Alle Modale nutzen `<Modal>` als Container | must |
| 2 | ESC schliesst jeden Dialog | must |
| 3 | Backdrop-Click schliesst (ausser bei unsaved changes) | must |
| 4 | Focus-Trap aktiv bei offenem Modal | must |
| 5 | `aria-modal="true"` + `role="dialog"` auf jedem Modal | must |
| 6 | grep `modalOverlay` = 0 Treffer nach Abschluss | must |
| 7 | `npx tsc --noEmit` = 0 Fehler | must |
## Abschluss
- [ ] Modal-Komponente erweitert und dokumentiert
- [ ] useFormModal Hook erstellt
- [ ] Alle Seiten migriert
- [ ] CSS-Cleanup (modalOverlay entfernt)
- [ ] layout.md oder eigene modal.md Referenz aktualisiert
- [ ] CHANGELOG-Eintraege
- [ ] Dieses Dokument -> 4-done/ verschoben