# UX Design Specification - Frontend ## 1. Purpose This document defines the target frontend UX for RpgRoller based on `REQUIREMENTS.md` and the latest review edits. It is the design baseline we will iterate on before implementing new frontend code. Primary goals: - Make campaign play flow fast: select character, roll, see results. - Keep role rules clear: player, GM, and visibility boundaries. - Preserve trust: deterministic behavior, clear validation, append-only log feel. - Keep the interface simple for live-session use on desktop, tablet, and mobile. ## 2. Scope In scope for this UX: - Authentication (register/login/logout) - Two authenticated screens: - `Play` screen for character sheet and log - `Campaign Management` screen for campaign details and management actions - Character create/edit with picker-selected active context - Skill create/edit - Skill rolling with public/private visibility - Campaign log with live updates Out of scope for v1 UX: - Observer role management UI (future role) - Advanced profile settings - Campaign invitations or approvals - Log filtering/search/export - First-time onboarding tours ## 3. Personas and Permissions ### Player - Can create and edit own characters. - Can create and edit skills on own characters. - Can roll own or authorized character skills. - Can see campaign log entries allowed by visibility rules. ### GM - All player capabilities for owned or authorized characters. - Can create campaigns and choose rulesets. - Can edit characters and skills in campaigns they GM. - Can view all rolls in their campaigns, including private rolls. ### Future Observer (non-v1) - Read-only campaign visibility, no mutation actions. ## 4. UX Principles 1. Context first: always show current campaign and active character status at top. 2. One action, one confirmation: each mutation gives immediate success/failure feedback. 3. Permission-aware UI: hide or disable actions the user cannot perform. 4. Real-time clarity: live updates should feel stable, not jittery. 5. Progressive disclosure: deep management stays outside the play screen. ## 5. Product Decisions from Review The following decisions are now locked for v1: 1. Campaign switching persistence: per tab/session, not global account-level persistence. 2. Edit UX: every edit uses an explicit edit button that opens a popup modal with a dedicated form and submit action. 3. Private roll presentation: visually differentiate private entries depending on viewer perspective (GM vs roller). 4. Log filtering: deferred, no filtering controls in v1. 5. Onboarding: no onboarding hints in v1. ## 6. Information Architecture The app has two top-level states: - Unauthenticated - Authenticated Authenticated state has two screens: 1. `Play` (default after login) 2. `Campaign Management` Global authenticated navigation: - Header includes app identity, current user chip, campaign context, connection status, and screen switch control. - Screen switch is always available: `Play` <-> `Campaign Management`. ## 7. Global Layout ### 7.1 Play Screen - Desktop (>= 1024px) - Top sticky header. - Main body is exactly two columns: - Left column (2/3 width): character-focused area. - Right column (1/3 width): live campaign log. Left column contains: - Character picker (icon tab strip) - One character sheet (selected character only) - Skills list for selected character - Roll controls - Last roll summary Right column contains: - Campaign log feed only Campaign details and management controls are excluded from this screen. ### 7.2 Play Screen - Tablet and Mobile (< 1024px) - Single active panel area. - Bottom navigation bar toggles between two views: - `Character` - `Log` - Character and log are not shown side-by-side on tablet/mobile. - Header remains visible with context and connection status. ### 7.3 Campaign Management Screen (all breakpoints) - Focused on campaign setup and administration. - Contains campaign details, campaign creation, campaign selection, and management operations. - Character sheet and rolling controls are not primary in this screen. ## 8. Key User Flows ### 8.1 First-time GM flow 1. Register 2. Login 3. Open `Campaign Management` 4. Create campaign with ruleset 5. Create or move character into campaign 6. Select character in picker (selection becomes active context) 7. Switch to `Play` 8. Create skill 9. Roll skill (public/private) 10. Confirm result appears in log ### 8.2 Player participation flow 1. Register/login 2. Open `Campaign Management` 3. Select accessible campaign 4. Create character in that campaign 5. Select character in picker (selection becomes active context) 6. Switch to `Play` 7. Add or edit skills 8. Roll and view log with visibility rules ### 8.3 GM oversight flow 1. Open `Play` 2. Switch between characters with icon tabs 3. Observe roll events in live log 4. Move to `Campaign Management` when campaign setup or details edits are needed ## 9. Screen Specifications ## 9.1 App Load and Session Restore States: - Initial: "Connecting..." - Healthy + anonymous: show auth view - Healthy + logged in: show `Play` screen - API unhealthy: show non-blocking banner with retry CTA Behavior: - Call health endpoint first, then rulesets and session context. - If session invalid or expired, clear local authenticated state and show auth view. ## 9.2 Authentication View Elements: - Register card: - Username - Display name - Password - Submit - Login card: - Username - Password - Submit Validation: - Username required - Display name required (register only) - Password required, min length 8 for register Feedback: - Inline field errors pre-submit - Top-level form error for server rejects (duplicate username, invalid credentials) - Success message after register ## 9.3 Shared Header (Authenticated) Shows: - Logged-in display name + username - Current campaign name (or "No campaign selected") - Active character summary (or "None selected") - Live state indicator: - Connected - Reconnecting - Offline fallback Actions: - Switch screen (`Play` / `Campaign Management`) - Manual refresh - Logout ## 9.4 Play Screen - Character Column (2/3) ### Character Picker - Horizontal icon tab control. - One icon per available character in the current campaign scope. - Active character has persistent visual highlight. - Selecting a tab changes the character sheet context. ### Character Sheet Shows selected character details: - Character name - Owner - Campaign affiliation - Active badge shown for the currently selected picker character Actions: - `Edit Character` button -> opens modal form ### Skills and Roll Commands Shows selected character skills list and selected skill details. Actions: - `Create Skill` button -> modal form - `Edit Skill` button -> modal form - d6 skill forms include: - `Wild dice` numeric field - `Allow fumble` toggle - Roll command panel: - Visibility selector (`public`, `private`) - `Roll Skill` primary action Last roll card: - Result total - Breakdown - Die-by-die visualization with states: `critical`, `fumble`, `wild`, `removed`, `added` - Visibility - Timestamp ## 9.5 Play Screen - Log Column (1/3) Shows chronological roll entries with: - Roller identity - Character + skill - Result and breakdown - Die-by-die visualization with states: `critical`, `fumble`, `wild`, `removed`, `added` - Visibility badge - Timestamp Visibility rules: - Public rolls visible to all participants. - Private rolls visible only to roller and GM. - No placeholders for hidden private rolls. Perspective styling for private rolls: - Roller view: private badge style A (for "you rolled private") - GM view: private badge style B (for "GM-visible private") ## 9.6 Campaign Management Screen This screen contains all campaign details and management options. Sections: 1. Campaign selector and campaign summary 2. Create campaign form (name + ruleset) 3. Campaign details card (name, ruleset, GM) 4. Character management list and actions Edit pattern: - All edits use explicit edit buttons. - Edit buttons open popup modals with dedicated forms. - No inline row editing. ## 9.7 Tablet/Mobile Bottom Bar Behavior Applies to both tablet and mobile in `Play` screen. Bottom bar items: - `Character` - `Log` Rules: - Exactly one panel active at a time. - Active tab state is preserved while user remains on current page session. - Roll action remains accessible in `Character` panel. - Connection status remains visible in header regardless of active panel. ## 10. Validation and Error UX Pre-submit client validation: - Required field checks for all forms - Password minimum length on register - Local non-empty checks for names and expressions Server error mapping: | Backend condition | UX behavior | |---|---| | `invalid_username`, `invalid_display_name`, `invalid_password` | Show field-level + summary errors in auth forms | | `duplicate_username` | Register username field error with suggestion to choose another | | `invalid_credentials` | Login summary error only (no account existence hints) | | `invalid_campaign_name`, `invalid_character_name`, `invalid_skill_name` | Field-level inline error in modal form | | `invalid_ruleset`, expression validation failures, `invalid_visibility` | Field-level error and helper text with valid examples | | `campaign_not_found`, `character_not_found`, `skill_not_found` | Non-blocking panel alert + auto-refresh relevant list | | `forbidden` | Explain permission rule and remove unavailable actions | | `unauthorized` | Clear session and return to auth view with message | | `no_active_character` | Prompt user to choose a character in picker and auto-sync active context | ## 11. Empty, Loading, and Disabled States Required empty states: - No campaigns yet - No characters in selected campaign - No skills for selected character - No log entries yet - No active character Loading patterns: - Skeleton rows for lists - Disabled form actions with spinner when mutation is in flight - Maintain prior data view during refresh to reduce layout jumps ## 12. Real-Time and Sync Rules - `Play` screen log is campaign-scoped. - Subscribe to SSE only when: - user is authenticated - campaign is selected - On state event: - refresh current character context data - refresh campaign log - On SSE failure: - exponential backoff reconnect - status indicator switches to "Reconnecting" - manual refresh remains available ## 13. Accessibility Requirements - Full keyboard operation for all controls. - Visible focus ring and logical tab order. - Labels for every input (placeholder is not label). - Contrast target >= WCAG AA. - Screen reader announcements for: - global success/error toasts - roll result updates - reconnect state changes - Icon-tab character picker must include readable text labels for assistive tech. ## 14. Content and Copy Guidance - Use plain language and short action labels. - Keep critical actions explicit: - "Create Campaign" - "Roll Skill" - Error tone: corrective and direct. - Date/time: local display with ISO tooltip. ## 15. Visual Direction (for implementation phase) - Theme: tabletop utility UI with clear hierarchy, not a generic admin dashboard. - Emphasize readability for dense gameplay sessions. - Character picker should use icon tabs with strong selected-state affordance. - Use color semantics: - success for roll completion - warning for validation needs - neutral role/visibility badges - Keep motion purposeful: - subtle log insert transitions - connection state transitions ## 16. Requirements Traceability | Requirement area | UX coverage | |---|---| | User management | Auth view with register/login/logout, secure failure messaging | | Campaign management | Dedicated `Campaign Management` screen with ruleset assignment and details | | Character management | Character picker + modal edit/create flows with selected-character active context | | Active character context | Persistent header context and activation CTA | | Skill management | Skill create/edit modals + ruleset-aware validation feedback | | Dice rolling | Visibility toggle + deterministic result display in `Play` screen | | Campaign log | Dedicated log column (desktop) and log tab (tablet/mobile) with permission filtering | | Edge constraints | Disabled/forbidden/unauthorized handling and recovery UX | ## 17. Next Iteration Targets 1. Define low-fidelity wireframes for `Play` and `Campaign Management`. 2. Define exact component contracts (props/state/events) for the frontend module split. 3. Define visual tokens (spacing, type scale, color roles) for implementation.