Add retakes, quiz templates, score history, due dates, CSV export, and prerequisites

- allow_retakes flag on items: quizzes, spelling tests, and assignments can all be retaken
- Quiz templates: save any quiz as a reusable template and load it into new items
- Score history: every quiz/test attempt logged to submission_history; click a gradebook score to see all attempts
- Due dates: optional due date per item, shown in course view and gradebook (overdue flagged with ⚠️)
- Gradebook CSV export: one-click download of any course gradebook
- Prerequisites: lock an item until a prior one is completed; locked items show 🔒 in course view

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
nmemmertandClaude Sonnet 4.6 committed 2026-07-14 13:22:58 -04:00
1 parent 23b24b5d21
commit 02909e1edc
6 files changed
+375 -39

No files matched your search

+24
View File
@@ -392,3 +392,27 @@ button.tiny { font-size: 0.75rem; padding: 0.15rem 0.5rem; }
.scan-provider-box legend { font-weight: 600; padding: 0 0.3rem; }
.radio-label { display: block; margin: 0.3rem 0; cursor: pointer; }
.radio-label input { margin-right: 0.4rem; }
/* ---------- new features: locked items, due dates, overdue, history, modal ---------- */
.today-row.locked {
opacity: 0.55;
cursor: not-allowed;
background: var(--bg);
border-color: var(--muted);
}
.due-date { color: var(--muted); font-size: 0.78rem; display: block; }
td.overdue, .overdue { background: var(--bad-bg) !important; }
.attempt-history { margin: 0.75rem 0; font-size: 0.9rem; }
.attempt-history summary { cursor: pointer; color: var(--accent); }
.attempt-history table { width: 100%; border-collapse: collapse; margin-top: 0.5rem; }
.attempt-history td { border: 1px solid #ddd; padding: 0.3rem 0.5rem; }
.modal {
position: fixed; inset: 0; background: rgba(0,0,0,0.45);
display: flex; align-items: center; justify-content: center; z-index: 100;
}
.modal-box {
background: var(--card); border-radius: var(--radius);
padding: 1.5rem; max-width: 520px; width: 90%; max-height: 80vh; overflow-y: auto;
}
.modal-box h3 { margin-bottom: 1rem; }
.modal-box .secondary { margin-top: 1rem; }