Commit Graph
77 Commits
Author SHA1 Message Date
hz c140b9a96c Fix CCS popup lifecycle and contrast 2026-08-04 07:10:36 -05:00
hz 300b230c03 Add weekly consistency goals 2026-08-01 04:14:39 -05:00
hz ecd5da9162 Add daily study missions 2026-08-01 04:02:24 -05:00
hz 8c439c6294 Add question bank mastery paths and gap questions 2026-07-31 23:46:46 -05:00
hz 53b85942d3 Merge main into production 2026-07-30 17:08:31 -05:00
hz 5488dec2c7 Lock submitted simulation answers 2026-07-30 16:54:12 -05:00
hz a08d0d9bf9 Fix long answer choice layout 2026-07-30 16:28:44 -05:00
hz ae6b37eb7d Make simulation block submission idempotent 2026-07-30 15:30:54 -05:00
hz c63227fcf5 Merge pull request 'Main' (#16) from main into production
Reviewed-on: admin/step3#16
2026-07-30 15:04:21 -05:00
hz 98518e8d39 Keep answered follow-ups expanded 2026-07-30 05:11:54 -05:00
hz fa5df8795f Reduce answer review scroll redraws 2026-07-30 05:02:03 -05:00
hz bf56f4192f Fix simulated exam question flow 2026-07-30 04:26:18 -05:00
hzandClaude Sonnet 5 efe60f36c5 Fix dashboard info-icon rendering and profile <null> display
Info badge: the icon was a PanelContainer using StyleBoxFlat corner
radius to fake a circle, with the radius exceeding half the box size,
causing visible artifacts. Replaced with a custom-drawn Control
(draw_arc) for a clean ring at any size, and added a hover tooltip
explaining what each stat card measures.

Profile: Dictionary.get(key, default) only falls back when the key is
missing, not when it's present with a null value, so a null
displayName rendered as the literal string "<null>" (str(null) in
GDScript) - including pre-filling the edit-profile dialog with it.
Added a shared string_field() helper that treats null the same as
missing, applied everywhere an account/preference string field is
displayed or edited.

Co-Authored-By: Claude Sonnet 5 <[email protected]>
2026-07-26 16:27:46 -05:00
hz 94e0e5dd70 Confirm passwords for external account creation 2026-07-26 14:52:41 -05:00
hz 500477b612 Add dashboard performance trends 2026-07-25 22:43:34 -05:00
hz 46953ee71a Reach Settings/Profile from the pause menu, with a way back
The pause menu (Escape during a question/CCS/flashcards run) only had
Resume/UI Sounds/Exit Run/Log Out. Settings already has an equivalent
"Interface sounds" toggle, so drop the duplicate from the pause menu.
More importantly, "player" and "ccs_player" hide the entire app shell
(header + sidebar), so there was no way to reach Settings or Profile
at all mid-session - add Profile/Settings buttons to the pause menu to
close that gap.

Navigating there follows the existing return_screen payload
convention (already used by simulation_history/results/review) rather
than inventing new navigation infrastructure: _navigate_from_pause()
remembers current_screen_name and passes it through show_screen's
payload. Both screens show a "Back to session" button when that's
set, and hide it otherwise (including on ordinary non-paused visits).

show_screen() unconditionally resumes the question timer via
_close_app_menu() as a side effect of any navigation, so
_navigate_from_pause() re-pauses it immediately when leaving "player" -
the timer then resumes for real, for free, when the user actually
returns via show_screen(return_screen).

progress_profile.gd rebuilds its whole child tree on every theme
toggle (_rebuild -> _build), which would otherwise wipe the button's
visibility - added _refresh_back_to_session_visibility(), called both
after _build() and from on_show(), so it survives a theme change while
paused.

Flipped tests/web_responsive_test.gd's assertion, which previously
required the pause menu NOT to have a Profile button.

Verified end-to-end headlessly: opening the pause menu from a live
"player" session, navigating to Settings and Profile, confirming
current_question_pause_started_at is correctly paused while away and
resumed on return, confirming the back-to-session button appears only
when reached via pause (not on ordinary nav), and confirming it
survives a dark/light theme toggle on the Profile screen.
2026-07-25 22:30:03 -05:00
hz 0e473343d0 Fix stale web_responsive_test icon assertion
It checked for a "DynamicQuestionsIcon" mode card that no longer
exists in study_selector.gd (that mode moved to its own nav item and
screen a while back), so it always failed. CCS Cases is now also
UAT-gated and won't be present in the default test environment either,
so point the check at Question Bank, the one mode card that's always
rendered.
2026-07-24 23:17:59 -05:00
hz 576b48d581 Fix toolbar gaps and theme toggle shape
- A toolbar icon that hides itself at runtime (labs, notes,
  flashcard, bookmark) left its text label behind, showing as an
  orphaned label floating in a gap. The label's wrapper now tracks
  the button's own visibility.
- The theme toggle used a distinct circular pill shape; changed it
  to match the same rounded-square box every other toolbar icon uses.
2026-07-24 19:55:49 -05:00
hz 974de67032 Redesign question bank screen to match new mockup
Adapts the quiz screen's header, toolbar, choice cards, and bottom bar
to the designer's new layout:

- Header: adds the RanaZe logo/wordmark and a question-progress bar +
  percentage alongside the existing "Question N of M" text.
- Toolbar: consolidates 12 icon-only/chip buttons into 6 labeled items
  (Text size, Calculator, Clear highlight, Notes, Bookmark, More), with
  a new "More" popup holding the rest (labs, flag, report, flashcard,
  theme toggle, feedback). The underlying buttons are reparented, not
  duplicated, so every existing theming/visibility/state call site
  keeps working unmodified.
- Category tag: shows the question's discipline (falling back to
  system) above the stem.
- Choice cards: every choice now renders as a subtly-bordered rounded
  card even before answering, not just a flat divider row; the
  currently-selected pre-submit choice shows a checkmark.
- Bottom bar: merges the Skip/Submit row and the timer row into one -
  Skip as a plain link, a centered "X of Y" progress bar, and a
  time slot that shows the existing countdown when a limit applies or
  a new count-up stopwatch ("Time elapsed") otherwise, plus a
  Ctrl+Enter/Cmd+Enter submit shortcut with a visible hint.
2026-07-24 02:28:22 -05:00
hz edcc0def5d Fix CCS category order search 2026-07-23 23:14:38 -05:00
hz 92c5688b55 Upgrade dynamic questions to authored parity 2026-07-23 14:11:18 -05:00
hz 50f07a77a5 Add exam-style question calculator 2026-07-23 05:19:12 -05:00
hz 8e216eac32 Rebuild CCS case workflow 2026-07-23 04:43:02 -05:00
hz 489b9c3d7c Fix text zoom not actually syncing, and expose it in Settings
Two real gaps meant the account-synced zoom (from the previous
"sync through the account" change) never reached the screen:
_load_cache() updated AccountProfileService.preferences but never
emitted profile_changed, so question_player.gd/ccs_service.gd (already
built and listening before login even happens) never found out a
cached value had loaded. And nothing forced a server refresh
right after login - it only fired if the user happened to open the
profile/progress screen, so a fresh device/session had no path to
the true synced value at all.

main.gd now calls AccountProfileService.refresh() once per login
(not on every silent token refresh) so the real preferences GET
always runs right after signing in, on any device.

Also added Question bank/CCS case text size steppers to the Settings
screen next to dark mode, per user request, reusing the same
AccountProfileService/CCSService plumbing as the in-screen A-/A+
buttons.
2026-07-23 04:37:45 -05:00
hz b3a8dec379 Simplify resolved wrong-answer explanation cards per design feedback
Drop the redundant header row (duplicate percentage badge + collapse
chevron), the "Why this is appropriate/less appropriate:"/"Why this
is incorrect:" heading labels, and the nested sub-box - now that
these cards live inside their own choice's colored border, all of
that was repeating what the color and position already say. Both the
selected-wrong-choice resolved follow-up and the never-selected
distractor cards now just show the plain explanation sentence, with
the leading "Correct."/"Incorrect." verdict word stripped too.

Removing the toggle chevron removes the only way to reach the
collapse/expand behavior, so that machinery (_collapse_resolved_followups,
_toggle_followup_state, the "collapsed" state field) comes out too
rather than linger unreachable.
2026-07-23 04:19:10 -05:00
hz d69a1fd0e3 Sync text zoom preference through the account instead of local settings
Local user://settings.cfg meant zoom level didn't follow a student
across devices/browsers. Question bank and CCS text scale now live on
the user's study profile in Mongo (QuestionTextScale/CcsTextScale),
synced through a new PUT /api/profile/me/text-scale endpoint and the
existing preferences GET/cache already used for study preferences.

Both question_player.gd and ccs_service.gd read the synced value at
startup and react to AccountProfileService.profile_changed so a value
pulled down after login (or changed from another session) applies
without a restart. Backend validates the 0.85-1.35 range and updates
only the field(s) provided via a targeted $set, so it can't clobber
the other scale or the unrelated study-profile preferences.
2026-07-23 03:59:02 -05:00
hz 4db5b9d374 Drop the redundant status icon and "Review: B..." label from follow-up panels
The choice button above the panel already shows the letter badge,
choice text, and percentage, so repeating them in the panel header
was redundant now that the panel is docked inside the choice's card.
Keeps the collapse toggle, now named FollowupToggle since the old
FollowupSummary button it lived on is gone.
2026-07-23 01:47:11 -05:00
hz b56d48d570 Fix eliminated-choice strikethrough disappearing on wrong/correct reveal
A choice that was crossed out (right-click) and also happened to be
locked as the submitted-wrong choice, or revealed as the correct
answer, silently lost its strikethrough because the percentage-badge
branches took precedence over the elimination check in the same
if/elif chain. Decoupled the two so a choice can show both the
strikethrough and its reveal percentage at once.
2026-07-22 23:10:41 -05:00
hz f17797becc Don't show the session-expiry warning to actively-used sessions
The warning was purely a token-expiry countdown with no concept of
user activity, so it interrupted people who had been clicking through
questions the whole time. AuthState now tracks real input activity
globally and silently refreshes the session in the background when
the user has interacted recently, only surfacing the "Stay logged in?"
dialog for sessions that are genuinely idle. A failed background
refresh still surfaces the dialog rather than silently logging the
user out.
2026-07-22 22:52:38 -05:00
hz 9f62444a63 Add a review-flag state for questions, independent of publish status
Flagged questions disappear from every student-facing surface (search,
exam simulation sampling, the missed-question review queue, bookmarks,
direct fetch) while staying published - flagging and unpublishing are
now separate, reversible actions with their own audit trail (who
flagged it, when, why). Backend-only for now: SUPER-only flag/unflag/
list endpoints, no client UI. Includes a one-time CLI sweep
(flag-media-questions) to flag every existing question with an image
so they can be reviewed.
2026-07-22 22:42:19 -05:00
hz e8d615985b Reveal the flashcard answer by tapping the card, not a separate button
Matches the mockup: the "Show Answer" button is replaced by an in-card
"Tap card to reveal answer" hint, and clicking anywhere on the card
reveals it (guarded the same way Space already was - only while at the
live card and not yet revealed).
2026-07-22 17:21:23 -05:00
hz 7f76ca0fdc Add system (curated) vs. user-uploaded flashcards
System decks/notes are owned by a reserved sentinel user id, reusing
all existing per-user store/index plumbing unchanged. Regular users
see them under a separate "Official Decks" section, can study them
with fully independent per-user FSRS progress (lazily materialized on
first visit), but can never edit or archive them - enforced both in
the client (no Edit/Archive controls) and server-side (ownership guard
on every mutating endpoint). Includes a small idempotent seed command
(`dotnet run -- seed-flashcards`) for testing, since there's no in-app
authoring UI yet.
2026-07-22 15:52:19 -05:00
hz 09b670d5d4 Close the gap between the flashcards study screen and the mockup
Add real session-history navigation (Previous/Next/Shuffle), compact
side panels, and a segmented progress row to match the mockup layout.
Flashcards now opens straight into Study, with library management
moved into the Options menu ("Manage Flashcards") and Export hidden
from the UI (Import stays). Shuffle is backed by a real, due-before-new
randomized pick on the backend, not a decorative toggle.
2026-07-22 00:43:52 -05:00
hz 70aa425fde Rebuild flashcard study screen from mockup, with real backend-backed stats
Study screen now matches the provided mockup's layout: a "Current
Deck" panel with a circular mastery-progress ring, and a "Spaced
Repetition" panel (New/Due/Learning/Review counts, streak, daily
goal) on either side of the card. Kept the app's real global sidebar
rather than the mockup's own nav, per direction.

Mastery/Streak/Daily Goal weren't tracked anywhere, so this adds real
backend support rather than showing fabricated numbers:
- Mastered = graduated to review state AND FSRS stability >= 21 days
  (FlashcardScheduleStore.MasteryStabilityDaysThreshold), stricter
  than the plain Review-state count
- CurrentStreakDays = consecutive UTC days with a review, computed
  from review-log timestamps in the new pure FlashcardScheduling
  .ComputeStreakDays (unit tested, habit-streak semantics: doesn't
  reset to 0 the instant a new day starts before today's first review)
- DailyGoal/ReviewsToday reuse the account's existing ReviewsPerDay
  setting rather than inventing a new one
Also removes the exit "X" button in favor of the same Escape/pause
menu the question-player flow uses (main.gd's shared app_menu, with
an "Exit Study Session" action), and adds a new circular_progress.gd
reusable ring control plus a real "Options" menu (bury/suspend the
current card) wired to schedule endpoints that had no UI before.
2026-07-21 23:20:14 -05:00
hz 72fb6e4776 Rework flashcards library to match the rest of the app's visual language
Compared side-by-side against Dashboard, the library screen used
entirely different visual primitives: a gradient primary button
Dashboard doesn't use anywhere, per-row bordered cards with low
contrast against the dark background, and a translucent pill badge
instead of the icon-circle pattern used everywhere else (stat tiles,
review queue, recent activity).

- Study/Save/Commit import now use Dashboard's actual primary button
  style (flat ROYAL_BLUE, not the login/session-dialog gradient)
- Added a stat-tile row (Due today / New available / Decks) using
  Dashboard's exact icon-circle + value + label construction, replacing
  the due/new counts previously crammed into the deck dropdown's text
- The note list now lives in one bordered card with a section title
  (matching Dashboard's chart/list panels) instead of each row being
  its own separate low-contrast card
- Per-row card-type indicator is now an icon circle (clipboard-list /
  notebook-pen) matching the Recent Activity list pattern, instead of
  a translucent color-coded pill badge
2026-07-21 22:47:21 -05:00
hz 7e19366dcb Redesign flashcards for visual hierarchy and button consistency
Study card: label the answer and "key takeaway" as distinct sections
with a real visible divider (previously an all-but-invisible
HSeparator) instead of one undifferentiated block of text. Also fixes
a real gap where a cloze card's extra field was silently dropped,
since only basic notes combined answer+extra into one label. Bigger
card, gradient Show-Answer button matching the app's signature CTA
style instead of a duller flat teal, and the Undo button now hides
itself when there's nothing to undo instead of sitting there disabled
looking identical to a real action.

Library: colored type badge per card (Basic/Cloze) instead of plain
gray text, more breathing room inside each row, Study promoted to the
same gradient CTA style, and Edit/Archive given a real secondary
button treatment instead of default theme buttons. Note editor fields
renamed ("Back / Extra takeaway" + a separate "Extra" field was
genuinely confusing) and now show which deck a card is being saved to.
2026-07-21 22:05:36 -05:00
hz 4dfbd811b9 Wire flashcard CSV/JSON import/export and fix theme/responsive gaps
Import and export were stubbed with status-text placeholders; wire them
to the existing backend endpoints with a real file picker (web JS
bridge or native FileDialog) and browser/desktop download, plus an
import preview with create/update/skip/error counts before commit.

Also fix the library and study screens' theme-refresh handlers, which
were no-op stubs so cards never restyled on a theme toggle, and add
responsive layout handling for narrow viewports.
2026-07-21 16:41:26 -05:00
hz 48a8c8361d Add flashcards feature with spaced repetition scheduling
Adds a full flashcards system: FSRS-based scheduling, cloze/basic
card types, CSV import/export, media storage, and study UI, wired
into navigation and the dashboard alongside existing question flows.
2026-07-21 15:08:52 -05:00
hz 29b89dc404 Remove redundant follow-up retry action 2026-07-20 23:59:07 -05:00
hz c2d000cc48 Add automated UAT smoke tests 2026-07-20 23:54:11 -05:00
hz 121e80b2ea Prefer high-performing distractors 2026-07-20 02:44:58 -05:00
hz dae3a31b71 Add legal consent and reliable external redirects 2026-07-20 02:16:20 -05:00
hz f93b7ac380 Complete resilient Steam login flow 2026-07-20 00:30:06 -05:00
hz d176640cff Rebrand app as RanaZe Step 3 Trainer 2026-07-20 00:04:29 -05:00
hz 743399f647 Improve donation defaults and light contrast 2026-07-19 23:12:51 -05:00
hz dec5e74aa7 Add Stripe donation flow 2026-07-19 22:26:33 -05:00
hz f12904bf73 Unify CCS case management flow 2026-07-19 21:29:24 -05:00
hz dacf2b89b2 Implement responsive profile and account data controls 2026-07-19 13:39:15 -05:00
hz 7508d4fe1d Implement persistent review queue 2026-07-19 12:51:24 -05:00
hz 2dcac51452 Add user progress dashboard 2026-07-18 23:45:38 -05:00