Lesson persistence and progress tracking
Created by: jedmund
Summary
- SwiftData persistence: LessonRecord (page progress), ActivityRecord (exercise/quiz attempts), ProgressStore with revision counter for reactivity
- Lessons resume at the furthest page on re-entry
- Exercises and quizzes block forward scrolling until complete
- Completion state hydrated from SwiftData on lesson open (exercises show score, quizzes show finished state)
- Activity rings on lesson cards (outer = page progress, inner = score)
- Exercise checkmarks on the lesson progress bar
- Keyboard fades in with spring animation on resume instead of popping in
Stacked on #6.
Test plan
-
Swipe through a lesson, hit Back, verify activity ring updates on the card -
Re-enter lesson, verify it resumes at the saved page -
Complete an exercise, leave and return, verify completion screen shows correct score -
Complete a quiz, leave and return, verify finished state with correct count -
Scroll past incomplete exercise/quiz is blocked with alert -
Scroll past completed exercise/quiz is allowed -
Resume on an interactive page: keyboard fades in smoothly after page appears -
Exercise markers appear on progress bar after completion