Persönliche Klausurlast pro Woche, Mitarbeit-Reset und Sitzplan-Strichliste
CI / build-and-test (push) Canceled after 0s
CI / build-and-test (push) Canceled after 0s
- Klausuren: neuer ExamWeekLoadService zählt eigene Klausuren je ISO-Woche über alle Kurse hinweg (Klassen-Kollisionen deckt bereits der externe Klausurplaner ab). Hinweis direkt im ExamDialog beim Datum, zusätzlich neue Dashboard-Karte "Klausurwochen" für die 60-Tage-Vorausschau. - Mitarbeit: Schnelleingabe-Dialog kann eine Bewertung jetzt per Entf auf "nicht bewertet" zurücksetzen (bisher nur im Sitzplatz-Dialog möglich). - Sitzplan: Strichliste "gemeldet"/"gemeldet und drangekommen" direkt auf der Sitzplatz-Kachel (ParticipationEntry.RaisedHandCount/CalledOnCount); schlägt im Sitzplatz-Dialog eine Quantitätsbewertung vor (ein Klick zum Übernehmen, nie automatisch). Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
@@ -24,6 +24,14 @@ public class ParticipationEntry
|
||||
// Bleibt für bereits gespeicherte Daten erhalten. Neue Schreibvorgänge setzen beide Felder.
|
||||
public bool HomeworkMissing { get; set; }
|
||||
public AttendanceStatus? Attendance { get; set; }
|
||||
// Strichliste im Sitzplan (Nutzer-Feedback): RaisedHandCount zählt jede beobachtete Meldung,
|
||||
// CalledOnCount die Teilmenge davon, bei der der Schüler auch drangekommen ist —
|
||||
// "drangekommen" ist immer auch eine Meldung und erhöht daher immer beide Zähler zugleich,
|
||||
// nie CalledOnCount allein. Ergibt nebenbei eine Aufrufgerechtigkeits-Quote
|
||||
// (CalledOnCount / RaisedHandCount) und schlägt die Quantitätsbewertung vor, siehe
|
||||
// ParticipationCountSuggestion.
|
||||
public int RaisedHandCount { get; set; }
|
||||
public int CalledOnCount { get; set; }
|
||||
public DateTime UpdatedAt { get; set; } = DateTime.UtcNow;
|
||||
}
|
||||
|
||||
@@ -160,3 +168,27 @@ public static class ParticipationRatingScale
|
||||
_ => value,
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Nutzer-Feedback: die Strichliste im Sitzplan (<see cref="ParticipationEntry.RaisedHandCount"/>)
|
||||
/// schlägt direkt eine Quantitätsbewertung vor — wie oft sich jemand meldet, ist ja bereits die
|
||||
/// Quantität. Nur ein Richtwert, kein fester Automatismus: die Lehrkraft übernimmt den Vorschlag
|
||||
/// per Klick oder ignoriert ihn. Bewusst nur für <see cref="AspectValueType.Scale5"/> (der
|
||||
/// Standardtyp des "quantity"-Aspekts) — für individuell umkonfigurierte Aspekttypen gäbe es keine
|
||||
/// sinnvolle, unmissverständliche Abbildung.
|
||||
/// </summary>
|
||||
public static class ParticipationCountSuggestion
|
||||
{
|
||||
public static int? SuggestQuantity(AspectValueType type, int raisedHandCount)
|
||||
{
|
||||
if (type != AspectValueType.Scale5) return null;
|
||||
return raisedHandCount switch
|
||||
{
|
||||
0 => -2,
|
||||
1 => -1,
|
||||
2 or 3 => 0,
|
||||
4 or 5 => 1,
|
||||
_ => 2,
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -15,7 +15,7 @@ public sealed class DashboardSettingsService
|
||||
public static readonly string[] DefaultCardOrder =
|
||||
[
|
||||
"today", "tasks", "calendar", "excuses", "upcoming",
|
||||
"corrections", "unplanned", "alerts", "attendance", "support", "groups",
|
||||
"corrections", "unplanned", "alerts", "attendance", "support", "groups", "examload",
|
||||
];
|
||||
|
||||
private readonly string _configPath;
|
||||
|
||||
@@ -0,0 +1,54 @@
|
||||
using System.Globalization;
|
||||
using LehrerApp.Core.Models;
|
||||
|
||||
namespace LehrerApp.Core.Services;
|
||||
|
||||
/// <summary>
|
||||
/// Zählt eigene Klausuren pro ISO-Kalenderwoche über alle Lerngruppen hinweg. Nutzer-Feedback:
|
||||
/// die klassenbezogene Kollisionsprüfung (mehrere Klausuren einer einzelnen Klasse in einer
|
||||
/// Woche) übernimmt bereits der schulische Klausurplaner (externes Klassenbuch) — was dort
|
||||
/// fehlt, ist die persönliche Belastung der Lehrkraft: mehr eigene Klausuren in derselben Woche
|
||||
/// bedeuten unabhängig von der Klasse mehr Erstellungsaufwand vorher und mehr Korrekturaufwand
|
||||
/// danach. Da eine LiteDB-Datei genau einem Nutzer gehört (siehe CLAUDE.md), sind "alle
|
||||
/// Klausuren in der Datenbank" bereits gleichbedeutend mit "meine Klausuren".
|
||||
/// </summary>
|
||||
public static class ExamWeekLoadService
|
||||
{
|
||||
/// Ab dieser Anzahl eigener Klausuren in derselben Woche gilt die Woche als spürbar belastet.
|
||||
/// Nutzer-Feedback: zwei Klausuren aus zwei unterrichteten Fächern in derselben Woche sind
|
||||
/// normal, eine dritte ist die eigentliche Häufung.
|
||||
public const int WarningThreshold = 3;
|
||||
|
||||
/// Anzahl Klausuren (ohne <paramref name="excludeExamId"/>, z.B. die gerade im Dialog
|
||||
/// bearbeitete), die in dieselbe ISO-Kalenderwoche wie <paramref name="date"/> fallen.
|
||||
public static int CountInSameWeek(IEnumerable<Exam> allExams, DateOnly date, Guid? excludeExamId = null)
|
||||
{
|
||||
var (year, week) = IsoWeek(date);
|
||||
return allExams.Count(e => e.Id != excludeExamId && IsoWeek(e.Date) == (year, week));
|
||||
}
|
||||
|
||||
/// Gruppiert die übergebenen Klausuren nach ISO-Kalenderwoche und liefert nur die Wochen mit
|
||||
/// mindestens <see cref="WarningThreshold"/> Klausuren, chronologisch sortiert — für einen
|
||||
/// vorausschauenden Überblick (z.B. Dashboard), nicht für die Einzelprüfung beim Anlegen.
|
||||
public static List<ExamWeekLoad> FindOverloadedWeeks(IEnumerable<Exam> exams) =>
|
||||
exams
|
||||
.GroupBy(e => IsoWeek(e.Date))
|
||||
.Where(g => g.Count() >= WarningThreshold)
|
||||
.Select(g => new ExamWeekLoad(g.Key.Year, g.Key.Week, WeekStart(g.Key.Year, g.Key.Week), g.Count()))
|
||||
.OrderBy(w => w.WeekStart)
|
||||
.ToList();
|
||||
|
||||
private static (int Year, int Week) IsoWeek(DateOnly date)
|
||||
{
|
||||
var dt = date.ToDateTime(TimeOnly.MinValue);
|
||||
return (ISOWeek.GetYear(dt), ISOWeek.GetWeekOfYear(dt));
|
||||
}
|
||||
|
||||
private static DateOnly WeekStart(int isoYear, int isoWeek) =>
|
||||
DateOnly.FromDateTime(ISOWeek.ToDateTime(isoYear, isoWeek, DayOfWeek.Monday));
|
||||
}
|
||||
|
||||
public readonly record struct ExamWeekLoad(int IsoYear, int IsoWeek, DateOnly WeekStart, int ExamCount)
|
||||
{
|
||||
public DateOnly WeekEnd => WeekStart.AddDays(6);
|
||||
}
|
||||
Reference in New Issue
Block a user