diff --git a/DEVLOG.md b/DEVLOG.md index 9072110..fd9ca74 100644 --- a/DEVLOG.md +++ b/DEVLOG.md @@ -6417,3 +6417,117 @@ Keine Commits in dieser Session. - frontend/vite.config.ts | 2 + --- +## 2026-09-07 12:40 – 12:42 (2m) +**Beschreibung:** Claude Code Session +**Projekt:** asb-material + +### Commits +- c18638a feat(dashboard): echtes Drag & Drop statt Pfeil-Buttons, moderneres Kachel-Design + +### Geänderte Dateien +- DEVLOG.md | 75 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- frontend/package-lock.json | 62 +++++++++++++++++++++++++++++++++++++++++++++++++++ +- frontend/package.json | 3 +++ +- frontend/src/components/ui/card.tsx | 2 +- +- frontend/src/pages/dashboard/DashboardPage.tsx | 79 ++++++++++++++++++++++++++++++++++++----------------------------- +- frontend/src/pages/dashboard/TileFrame.tsx | 64 ++++++++++++++++++++++++++-------------------------- +- frontend/src/pages/dashboard/tiles/KennzahlenTile.tsx | 21 ++++++++++-------- +- frontend/src/pages/dashboard/tiles/MaengelTile.tsx | 11 ++++----- + +--- +## 2026-09-07 13:16 – 13:17 (0m) +**Beschreibung:** Claude Code Session +**Projekt:** asb-material + +### Commits +Keine Commits in dieser Session. + +### Geänderte Dateien +- DEVLOG.md | 75 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- frontend/package-lock.json | 62 +++++++++++++++++++++++++++++++++++++++++++++++++++ +- frontend/package.json | 3 +++ +- frontend/src/components/ui/card.tsx | 2 +- +- frontend/src/pages/dashboard/DashboardPage.tsx | 79 ++++++++++++++++++++++++++++++++++++----------------------------- +- frontend/src/pages/dashboard/TileFrame.tsx | 64 ++++++++++++++++++++++++++-------------------------- +- frontend/src/pages/dashboard/tiles/KennzahlenTile.tsx | 21 ++++++++++-------- +- frontend/src/pages/dashboard/tiles/MaengelTile.tsx | 11 ++++----- + +--- +## 2026-09-07 13:19 – 13:20 (0m) +**Beschreibung:** Claude Code Session +**Projekt:** asb-material + +### Commits +Keine Commits in dieser Session. + +### Geänderte Dateien +- DEVLOG.md | 75 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- frontend/package-lock.json | 62 +++++++++++++++++++++++++++++++++++++++++++++++++++ +- frontend/package.json | 3 +++ +- frontend/src/components/ui/card.tsx | 2 +- +- frontend/src/pages/dashboard/DashboardPage.tsx | 79 ++++++++++++++++++++++++++++++++++++----------------------------- +- frontend/src/pages/dashboard/TileFrame.tsx | 64 ++++++++++++++++++++++++++-------------------------- +- frontend/src/pages/dashboard/tiles/KennzahlenTile.tsx | 21 ++++++++++-------- +- frontend/src/pages/dashboard/tiles/MaengelTile.tsx | 11 ++++----- + +--- +## 2026-09-07 13:21 – 13:22 (0m) +**Beschreibung:** Claude Code Session +**Projekt:** agents + +### Commits +- 726d6e2 chore(agents): react/tailwind/css/html-expert Subagenten aus 0xfurai/claude-code-subagents geladen + +### Geänderte Dateien +- .claude/agents/DEVLOG.md | 20 ++++++++++++++++++++ +- .claude/agents/css-expert.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/html-expert.md | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/react-expert.md | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/tailwind-expert.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ + +--- +## 2026-09-07 13:23 – 13:24 (0m) +**Beschreibung:** Claude Code Session +**Projekt:** asb-material + +### Commits +Keine Commits in dieser Session. + +### Geänderte Dateien +- .claude/agents/DEVLOG.md | 20 ++++++++++++++++++++ +- .claude/agents/css-expert.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/html-expert.md | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/react-expert.md | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/tailwind-expert.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ + +--- +## 2026-09-07 13:24 – 13:24 (0m) +**Beschreibung:** Claude Code Session +**Projekt:** asb-material + +### Commits +Keine Commits in dieser Session. + +### Geänderte Dateien +- .claude/agents/DEVLOG.md | 20 ++++++++++++++++++++ +- .claude/agents/css-expert.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/html-expert.md | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/react-expert.md | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/tailwind-expert.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ + +--- +## 2026-09-07 13:25 – 13:25 (0m) +**Beschreibung:** Claude Code Session +**Projekt:** asb-material + +### Commits +Keine Commits in dieser Session. + +### Geänderte Dateien +- .claude/agents/DEVLOG.md | 20 ++++++++++++++++++++ +- .claude/agents/css-expert.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/html-expert.md | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/react-expert.md | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ +- .claude/agents/tailwind-expert.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ + +--- diff --git a/frontend/src/pages/dashboard/DashboardPage.tsx b/frontend/src/pages/dashboard/DashboardPage.tsx index 6db3a1c..bc475da 100644 --- a/frontend/src/pages/dashboard/DashboardPage.tsx +++ b/frontend/src/pages/dashboard/DashboardPage.tsx @@ -94,40 +94,55 @@ export function DashboardPage() { useSensor(KeyboardSensor, { coordinateGetter: sortableKeyboardCoordinates }) ); - function dragEnde(event: DragEndEvent) { - const { active, over } = event; - if (!over || active.id === over.id) return; - const von = layout.reihenfolge.indexOf(active.id as DashboardTileId); - const nach = layout.reihenfolge.indexOf(over.id as DashboardTileId); - if (von === -1 || nach === -1) return; - const neuesLayout = { ...layout, reihenfolge: arrayMove(layout.reihenfolge, von, nach) }; - setLayout(neuesLayout); - layoutSpeichern(neuesLayout); - } + const aktualisiereLayout = useCallback((aendern: (bisherig: typeof layout) => typeof layout) => { + setLayout((bisherig) => { + const neuesLayout = aendern(bisherig); + layoutSpeichern(neuesLayout); + return neuesLayout; + }); + }, []); - function ausblendenUmschalten(id: DashboardTileId) { - const istAusgeblendet = layout.ausgeblendet.includes(id); - const neuesLayout = { - ...layout, - ausgeblendet: istAusgeblendet ? layout.ausgeblendet.filter((x) => x !== id) : [...layout.ausgeblendet, id], - }; - setLayout(neuesLayout); - layoutSpeichern(neuesLayout); - } + const dragEnde = useCallback( + (event: DragEndEvent) => { + const { active, over } = event; + if (!over || active.id === over.id) return; + aktualisiereLayout((bisherig) => { + const von = bisherig.reihenfolge.indexOf(active.id as DashboardTileId); + const nach = bisherig.reihenfolge.indexOf(over.id as DashboardTileId); + if (von === -1 || nach === -1) return bisherig; + return { ...bisherig, reihenfolge: arrayMove(bisherig.reihenfolge, von, nach) }; + }); + }, + [aktualisiereLayout] + ); - function groesseAendern(id: DashboardTileId) { - const aktuelle = layout.groessen[id] ?? "normal"; - const naechsteIndex = (GROESSEN_REIHENFOLGE.indexOf(aktuelle) + 1) % GROESSEN_REIHENFOLGE.length; - const neuesLayout = { ...layout, groessen: { ...layout.groessen, [id]: GROESSEN_REIHENFOLGE[naechsteIndex] } }; - setLayout(neuesLayout); - layoutSpeichern(neuesLayout); - } + const ausblendenUmschalten = useCallback( + (id: DashboardTileId) => { + aktualisiereLayout((bisherig) => { + const istAusgeblendet = bisherig.ausgeblendet.includes(id); + return { + ...bisherig, + ausgeblendet: istAusgeblendet ? bisherig.ausgeblendet.filter((x) => x !== id) : [...bisherig.ausgeblendet, id], + }; + }); + }, + [aktualisiereLayout] + ); - function layoutZuruecksetzen() { - const neuesLayout: typeof layout = { reihenfolge: STANDARD_REIHENFOLGE, ausgeblendet: [], groessen: {} }; - setLayout(neuesLayout); - layoutSpeichern(neuesLayout); - } + const groesseAendern = useCallback( + (id: DashboardTileId) => { + aktualisiereLayout((bisherig) => { + const aktuelle = bisherig.groessen[id] ?? "normal"; + const naechsteIndex = (GROESSEN_REIHENFOLGE.indexOf(aktuelle) + 1) % GROESSEN_REIHENFOLGE.length; + return { ...bisherig, groessen: { ...bisherig.groessen, [id]: GROESSEN_REIHENFOLGE[naechsteIndex] } }; + }); + }, + [aktualisiereLayout] + ); + + const layoutZuruecksetzen = useCallback(() => { + aktualisiereLayout(() => ({ reihenfolge: STANDARD_REIHENFOLGE, ausgeblendet: [], groessen: {} })); + }, [aktualisiereLayout]); async function monitorUmschalten() { if (monitorModus) { @@ -234,7 +249,14 @@ export function DashboardPage() { Monitor beenden )} - {fehler &&
Lade…
} {bearbeitenModus && layout.ausgeblendet.length > 0 && (Keine bald ablaufenden Chargen.
; } @@ -26,3 +27,5 @@ export function AblaufdatenTile({ ablaufdaten }: Props) { ); } + +export const AblaufdatenTile = memo(AblaufdatenTileKomponente); diff --git a/frontend/src/pages/dashboard/tiles/AktivitaetTile.tsx b/frontend/src/pages/dashboard/tiles/AktivitaetTile.tsx index 5d6f9c6..11c9714 100644 --- a/frontend/src/pages/dashboard/tiles/AktivitaetTile.tsx +++ b/frontend/src/pages/dashboard/tiles/AktivitaetTile.tsx @@ -1,3 +1,4 @@ +import { memo } from "react"; import { Link } from "react-router-dom"; import type { HistorieEintrag } from "../../../api/types"; @@ -7,7 +8,7 @@ interface Props { aktivitaet: HistorieEintrag[]; } -export function AktivitaetTile({ aktivitaet }: Props) { +function AktivitaetTileKomponente({ aktivitaet }: Props) { if (aktivitaet.length === 0) { returnNoch keine Ereignisse.
; } @@ -32,3 +33,5 @@ export function AktivitaetTile({ aktivitaet }: Props) { ); } + +export const AktivitaetTile = memo(AktivitaetTileKomponente); diff --git a/frontend/src/pages/dashboard/tiles/AufgabenTile.tsx b/frontend/src/pages/dashboard/tiles/AufgabenTile.tsx index c495abd..745270e 100644 --- a/frontend/src/pages/dashboard/tiles/AufgabenTile.tsx +++ b/frontend/src/pages/dashboard/tiles/AufgabenTile.tsx @@ -1,3 +1,4 @@ +import { memo } from "react"; import { Link } from "react-router-dom"; import type { Einsatzbereitschaft, Kennzahlen } from "../types"; @@ -11,7 +12,7 @@ interface Props { bereitschaft: Einsatzbereitschaft; } -export function AufgabenTile({ +function AufgabenTileKomponente({ kennzahlen, maengelNeuAnzahl, maengelKritischAnzahl, @@ -50,9 +51,11 @@ export function AufgabenTile({ return ({kennzahlen.anzahl_offener_fehlbestaende}
@@ -20,3 +22,5 @@ export function KennzahlenTile({ kennzahlen }: Props) {Keine anstehenden oder überfälligen Geräteprüfungen.
; } return (Keine bald ablaufenden Qualifikationen.
; } @@ -24,3 +26,5 @@ export function QualifikationTile({ qualifikationsablaeufe }: Props) { ); } + +export const QualifikationTile = memo(QualifikationTileKomponente);