Phase 2: Round Scoring - iOS Roadmap

Phase: 2 Status: In Progress (2a complete, 2b-2f planned) Start Date: 2025-11-20 Estimated Completion: 2-3 weeks (part-time) or 1 week (full-time)


Overview

Phase 2 implements complete round scoring functionality for iOS, achieving feature parity with the Android app. This phase builds on the shared KMP code that provides 90-95% of the business logic, requiring only UI implementation and platform bridging.

Core Objective: Enable iOS users to create rounds, score arrows during practice sessions, view round history, and analyze performance statistics.


Current Status

✅ Phase 2a: Round Creation (PR #284)

Status: In review Completed: 2025-11-21 Effort: 8 hours

What Was Built:

  • RoundCreationViewModel.swift - Swift wrapper around KMP Round entity with Combine-based form validation
  • RoundCreationView.swift - Comprehensive 6-section form (407 lines)
  • Quick Start templates (18m Indoor, 70m Outdoor)
  • Auto-selection of scoring systems based on target size
  • Real-time validation with disabled submit when invalid
  • Summary card with Total Arrows and Max Possible Score calculations
  • Mock repository implementation (save doesn’t persist yet)

Testing Complete:

  • ✅ Quick Start templates auto-fill correctly
  • ✅ Manual entry with validation works
  • ✅ Target size changes auto-update scoring system
  • ✅ Form reset via Cancel works
  • ✅ Validation prevents invalid submission

Known Limitations:

  • Uses mock repository (rounds don’t persist)
  • No navigation to active scoring
  • Bow setup defaults to 0 (no selection UI)
  • Single user only (no multi-participant support)

PR: https://github.com/blamechris/archery-apprentice/pull/284


Remaining Phases

📋 Phase 2b: Round Persistence & Repository Integration

Status: Planned Estimated Effort: 4-6 hours Dependencies: RoundRepository KMP migration Priority: High (unblocks 2c-2e)

Objective

Wire up Round Creation to actually save data by migrating RoundRepository to shared KMP module and integrating with RoundCreationViewModel.

Tasks

  1. Migrate RoundRepository to KMP shared module

    • Current location: app/src/main/java/com/archeryapprentice/domain/repository/RoundRepository.kt (Android-only)
    • Target location: shared/data/src/commonMain/kotlin/.../repositories/RoundRepository.kt
    • Expose to iOS via KMP framework
    • Ensure RoundDao is also shared (if not already)
  2. Update RoundCreationViewModel to use real repository

    • Remove mock implementation (lines 192-198 in current PR)
    • Inject RoundRepository via KMP
    • Handle actual database saves with proper error handling
    • Return real round IDs from database
  3. Add error handling for database operations

    • Network errors (if syncing to Firebase)
    • Database constraint violations
    • Disk space issues
    • User-friendly error messages in UI
  4. Test end-to-end round creation

    • Create round via iOS UI
    • Verify database persistence
    • Confirm round appears in list (Phase 2c)

Success Criteria

  • ✅ Rounds persist to database after creation
  • ✅ Round IDs are returned from repository
  • ✅ Error handling covers all failure modes
  • ✅ iOS and Android share same repository code

Implementation Guide

See: Round Persistence Implementation Guide


📋 Phase 2c: Round History List

Status: Planned Estimated Effort: 6-8 hours Dependencies: Phase 2b (needs real data to display) Priority: High (core feature)

Objective

Display list of created rounds in RoundsTabView with filtering, sorting, and navigation to details/scoring.

Tasks

  1. Create RoundListView component

    • LazyVStack with round cards
    • Each card shows: Round name, date, distance, target size, score summary
    • Tap to view details or resume scoring
    • Pull-to-refresh functionality
    • Empty state (already exists)
  2. Create RoundListViewModel

    • Fetch rounds from RoundRepository
    • Filter by status (planned, in-progress, completed)
    • Sort by date (most recent first)
    • Handle loading and error states
    • Reactive updates when rounds change
  3. Update RoundsTabView

    • Replace empty state with RoundListView when rounds exist
    • Keep “Create Round” button in toolbar
    • Add filter/sort options (optional for MVP)
    • Smooth navigation transitions

Success Criteria

  • ✅ Round list displays all created rounds
  • ✅ List updates reactively when rounds are added
  • ✅ Tapping a round navigates to appropriate screen
  • ✅ Empty state shown when no rounds exist

Design Reference

Android RoundListScreen.kt (if exists, otherwise design from scratch to match iOS patterns)

Implementation Guide

See: Round List Implementation Guide


📋 Phase 2d: Active Scoring Screen

Status: Planned Estimated Effort: 12-16 hours Dependencies: Phase 2b (needs persistence) Priority: High (core feature)

Objective

Allow users to score arrows during a round with a clean, tappable interface matching Android functionality.

Tasks

  1. Create ActiveScoringView

    • Large, tappable score buttons (0-10 + X) in grid layout
    • Current progress display (End 1 of 10, Arrow 1 of 3)
    • Running total score with end subtotal
    • Undo last arrow button
    • End completion button (advance to next end)
    • Round completion detection and navigation
  2. Create ActiveScoringViewModel

    • Manage current end/arrow state
    • Validate score entries (check against scoring system rules)
    • Calculate running totals and averages
    • Save scores to database via RoundRepository
    • Handle end completion logic
    • Support undo functionality
  3. Navigation Integration

    • After creating round in Phase 2a → navigate to ActiveScoringView
    • From round list → tap in-progress round → resume scoring
    • From round list → tap planned round → start scoring
    • After completing round → navigate to Round Details
  4. State Persistence

    • Save arrow scores incrementally (don’t lose data on app close)
    • Resume scoring at correct end/arrow position
    • Handle app backgrounding gracefully

Success Criteria

  • ✅ Score entry is fast and intuitive
  • ✅ Running totals calculate correctly
  • ✅ Undo functionality works
  • ✅ End completion advances properly
  • ✅ Round completion detected and navigates
  • ✅ State persists across app sessions

Design Reference

Android ActiveScoringScreen.kt - match UI/UX patterns and behavior

Implementation Guide

See: Active Scoring Implementation Guide


📋 Phase 2e: Round Details & Statistics

Status: Planned Estimated Effort: 10-12 hours Dependencies: Phase 2d (needs completed rounds) Priority: Medium (nice-to-have for MVP)

Objective

View completed rounds with comprehensive statistics and end-by-end breakdown.

Tasks

  1. Create RoundDetailsView

    • Round summary header (name, date, distance, target, total score)
    • End-by-end breakdown table
    • Statistics section:
      • Average per arrow
      • Accuracy percentage
      • X-count and 10-count
      • Consistency metrics
    • Share/export button (optional)
    • Charts/graphs (future enhancement)
  2. Create RoundDetailsViewModel

    • Fetch round by ID from repository
    • Fetch all ends and arrows for round
    • Calculate statistics (leverage shared KMP logic if available)
    • Format data for display
    • Handle sharing/export functionality
  3. Navigation Integration

    • From round list → tap completed round → RoundDetailsView
    • Breadcrumb navigation back to list
    • Option to view in-progress rounds (show stats so far)

Success Criteria

  • ✅ Round details display all relevant information
  • ✅ Statistics calculate correctly
  • ✅ End-by-end breakdown is clear
  • ✅ Navigation flows smoothly

Design Reference

Android RoundDetailsScreen.kt

Implementation Guide

See: Round Details Implementation Guide


📋 Phase 2f: iOS UI Testing

Status: Planned Estimated Effort: 8-10 hours Dependencies: Phases 2a-2e complete Priority: Medium (deferred but recommended)

Objective

Add automated UI tests for Round Creation and Scoring to ensure quality and prevent regressions.

Tasks

  1. Set up XCUITest framework

    • Create UI test target in Xcode
    • Configure test schemes
    • Set up test data fixtures
  2. Write UI tests for Round Creation (Phase 2a)

    • Test Quick Start templates fill correctly
    • Test manual entry with validation
    • Test error states and alerts
    • Test form reset functionality
    • Test auto-selection logic
  3. Write UI tests for Active Scoring (Phase 2d)

    • Test score entry workflow
    • Test end completion
    • Test undo functionality
    • Test running total calculations
    • Test round completion
  4. Write UI tests for Round List (Phase 2c)

    • Test list displays rounds
    • Test navigation to details/scoring
    • Test empty state
    • Test pull-to-refresh

Success Criteria

  • ✅ Test coverage matches Android test coverage level
  • ✅ All critical paths have automated tests
  • ✅ Tests run reliably in CI/CD (if configured)

Implementation Guide

See: iOS Testing Strategy


Timeline Estimates

By Phase

PhaseDescriptionEffortStatus
2aRound Creation8 hours✅ Complete (in review)
2bRound Persistence4-6 hours📋 Planned
2cRound History List6-8 hours📋 Planned
2dActive Scoring12-16 hours📋 Planned
2eRound Details10-12 hours📋 Planned
2fUI Testing8-10 hours📋 Planned
Total48-60 hours

Timeline Scenarios

Part-Time Development (10-15 hours/week):

  • Optimistic: 3-4 weeks
  • Realistic: 4-5 weeks
  • Conservative: 5-6 weeks (accounting for blockers and iteration)

Full-Time Development (40 hours/week):

  • Optimistic: 1.5 weeks
  • Realistic: 2 weeks
  • Conservative: 2.5 weeks

Recommended Approach: Incremental PRs for each phase (2b → 2c → 2d → 2e → 2f)


Dependencies & Blockers

Critical Dependencies

  1. RoundRepository KMP Migration (Phase 2b)

    • Current State: Android-only repository
    • Required: Move to shared module for iOS access
    • Effort: 4-6 hours
    • Can Be Parallel: Yes (Android-focused dev can handle)
  2. KMP-NativeCoroutines Configuration

    • Current State: Likely already configured from Phase 1
    • Required: For Flow-based repository methods
    • Blocker: Low risk (should already work)

Nice-to-Have Dependencies

  1. Shared Statistics Logic

    • Current State: Unknown if exists in shared module
    • Impact: Phase 2e implementation effort
    • Fallback: Implement statistics in Swift if needed
  2. Shared Validation Logic

    • Current State: Some exists (ScoringSystem validation)
    • Impact: Phase 2d score validation
    • Fallback: Minimal Swift validation code

Key Decisions & Recommendations

1. Should RoundRepository migration block PR #284?

Question: Should we merge PR #284 (Round Creation with mock) before migrating RoundRepository?

Options:

  • Option A: Merge #284 with mock, then do repository migration in Phase 2b PR
  • Option B: Block #284 until RoundRepository is ready

Recommendation: Option A - Merge with mock first

Rationale:

  • Incremental delivery is better than big-bang PRs
  • Mock is acceptable for MVP validation
  • UI can be reviewed independently of persistence
  • Reduces risk of merge conflicts
  • Allows Phase 2b to focus solely on repository integration

Decision: Merge PR #284, tackle persistence in Phase 2b


2. What’s the priority order for Phase 2b-2f?

Question: Should phases be implemented sequentially or can some be parallelized?

Recommendation: Sequential: 2b → 2c → 2d → 2e → 2f

Rationale:

  • 2b must be first (all others need real data persistence)
  • 2c builds on 2b (list needs persisted rounds)
  • 2d builds on 2c (scoring needs round selection from list)
  • 2e builds on 2d (details need completed rounds)
  • 2f can be parallel (testing can start once features are stable)

Alternative: 2f (testing) can begin in parallel with 2d/2e implementation


3. Should iOS testing be required before Phase 2 is “done”?

Question: Is Phase 2f mandatory or nice-to-have?

Recommendation: Yes, add basic XCUITest coverage

Rationale:

  • Quality bar should match Android
  • Automated tests prevent regressions
  • iOS UI tests are straightforward with XCTest
  • Establishes testing pattern for future phases

Minimum Coverage:

  • Round creation (Quick Start + manual entry)
  • Score entry workflow
  • Round list display

Decision: Phase 2f is required for Phase 2 completion


4. How long will full Phase 2 iOS implementation take?

Question: What’s a realistic timeline?

Estimate: 48-60 hours total

  • 2a: 8 hours ✅ (complete)
  • 2b-2f: 40-52 hours (remaining)

Timeline:

  • Part-time (10-15 hrs/week): 4-5 weeks
  • Full-time (40 hrs/week): 1.5-2 weeks

Recommendation: Plan for 4-5 weeks with incremental PRs


5. Are there any KMP migrations needed?

Question: What shared code needs to be migrated/exposed?

Required:

  • RoundRepository - Must move to shared module (Phase 2b blocker)

Already Available:

  • ✅ Round entity (shared/database)
  • ✅ ScoringSystem, Distance, TargetSize enums (shared/presentation)
  • ✅ KMP-NativeCoroutines (Phase 1)

Unknown:

  • ❓ Statistics calculation logic (may need investigation for Phase 2e)

Recommendation: Tackle RoundRepository in Phase 2b, investigate statistics during Phase 2e planning


Success Criteria

Phase 2 is complete when:

  • ✅ Users can create rounds via iOS app
  • ✅ Rounds persist to database
  • ✅ Round list displays all created rounds
  • ✅ Users can score arrows during a round
  • ✅ Completed rounds show detailed statistics
  • ✅ Basic UI test coverage exists
  • ✅ iOS functionality matches Android parity for round scoring

Implementation Guides

iOS Phase Documentation

GitHub References


Next Steps

Immediate (This Week)

  1. Review and merge PR #284 (Round Creation)
  2. Begin Phase 2b planning (RoundRepository migration)
  3. Create Phase 2b implementation PR

Short-Term (Next 2 Weeks)

  1. Complete Phase 2b (Round Persistence)
  2. Complete Phase 2c (Round List)
  3. Begin Phase 2d (Active Scoring)

Medium-Term (Next 3-5 Weeks)

  1. Complete Phase 2d (Active Scoring)
  2. Complete Phase 2e (Round Details)
  3. Complete Phase 2f (UI Testing)
  4. Mark Phase 2 as complete

Last Updated: 2025-11-21 Status: Phase 2a complete, 2b-2f planned Estimated Completion: 4-5 weeks (part-time)