- Replace digital PSI readout with 3-column abacus display
- Replace tick mark labels (0, 50, 100, 150) with mini abacuses
- Use invisible column posts and proper sizing for readability
- Expand gauge dimensions to accommodate abacus labels without clipping
- Show inactive beads on dial indicators for place value clarity
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Add hideInactiveBeads to AbacusTarget for cleaner minimal display
- Improve vertical centering with translateY adjustment in equations
- Apply changes consistently across practice, survival, and sprint modes
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Apply global columnPosts property as fallback when rendering column rods
- Fix reckoning bar to span only across actual columns instead of full SVG width
- Column-specific columnPost styling still takes precedence over global
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
# [1.6.0](https://github.com/antialias/soroban-abacus-flashcards/compare/abacus-react-v1.5.1...abacus-react-v1.6.0) (2025-10-01)
### Bug Fixes
* align all bottom UI elements to same 20px baseline ([076c97a](076c97abac))
* align bottom-positioned UI elements ([227cfab](227cfabf11))
* change pressure gauge to fixed positioning to stay above terrain ([1b11031](1b11031598))
* change question display to fixed positioning with higher z-index ([4ac8758](4ac8758957))
* correct emoji category group IDs to match Unicode CLDR ([b2a21b7](b2a21b79ad))
* defer URL update until game starts ([12c54b2](12c54b27b7))
* delay passenger display update until train resets ([e06a750](e06a750454))
* eliminate rail jaggies on sharp curves by increasing sampling density ([46d4af2](46d4af2bda))
* ensure passengers only travel forward on train route ([8ad3144](8ad3144d2d))
* increase question display zIndex to stay above terrain ([8c8b8e0](8c8b8e08b4))
* move fontWeight to style object for station names ([05a3ddb](05a3ddb086))
* only show configuration gear icon for players 1 and 2 ([d0a3bc7](d0a3bc7dc1))
* passengers now board/disembark based on their car position, not locomotive ([96782b0](96782b0e7a))
* position tunnels at absolute viewBox edges ([1a5fa28](1a5fa2873b))
* prevent layout shift when selecting Steam Sprint mode ([73a5974](73a59745a5))
* prevent multiple passengers from boarding same car in single frame ([63b0b55](63b0b552a8))
* prevent premature passenger display during route transitions ([fe9ea67](fe9ea67f56))
* prevent random passenger repopulation during route transitions ([db56ce8](db56ce89ee))
* prevent route celebration from immediately reappearing ([1a80934](1a8093416e))
* reduce landmark size from 4.0x to 2.0x multiplier ([c928e90](c928e90785))
* remove double PageWithNav wrapper on matching page ([b58bcd9](b58bcd92ee))
* remove duplicate CAR_SPACING and MAX_CARS declarations ([e704a28](e704a28524))
* remove duplicate previousPassengersRef declaration ([fad8636](fad8636763))
* remove hard-coded car count from game loop ([6c90a68](6c90a68c49))
* remove unnecessary zIndex from question display ([db52e14](db52e14dfe))
* reset momentum and pressure when starting new route ([3ea88d7](3ea88d7a5a))
* smooth rail curves and deterministic track generation ([4f79c08](4f79c08d73))
* stabilize route completion threshold to prevent stuck trains ([b7233f9](b7233f9e4a))
* use displayPassengers for station rendering in RailroadTrackPath ([a9e0d19](a9e0d19734))
* use style fontSize instead of attribute for landmarks ([ebc6894](ebc6894746))
* wrap animated pressure value in animated.span to prevent React error ([5c5954b](5c5954be74))
### Features
* add category browsing and scrolling to emoji picker ([616a50e](616a50e234))
* add complement display options and unify equation display ([2ed7b2c](2ed7b2cbf8))
* add Complement Race game with three unique game modes ([582bce4](582bce411f))
* add configuration access to active player emojis in prominent nav ([6049a7f](6049a7f6b7))
* add configuration access to fullscreen player selection ([b85968b](b85968bcb6))
* add CSS animations and visual feedback system ([80e33e2](80e33e25b3))
* add direct URL routes for each game mode ([a08f053](a08f0535bf))
* add initialStyle prop to ComplementRaceProvider ([f3bc2f6](f3bc2f6d92))
* add interactive remove buttons for players in mini nav ([fa1cf96](fa1cf96789))
* add magnifying glass preview on emoji hover ([2c88b6b](2c88b6b5f3))
* add mini app nav to arcade page ([a854fe3](a854fe3dc9))
* add passenger boarding system with station-based pickup ([23a9016](23a9016245))
* add prominent game context display to mini nav with smooth transitions ([8792393](8792393956))
* add realistic mountains with peaks and ground terrain ([99cdfa8](99cdfa8a0b))
* add smooth spring animations to pressure gauge ([863a2e1](863a2e1319))
* add train car system with smooth boarding/disembarking animations ([1613912](1613912740))
* add Web Audio API sound effects system with 16 sound types ([90ba866](90ba86640c))
* create mode selection landing page for Complement Race ([1ff9695](1ff9695f69))
* create PlayerConfigDialog component for player customization ([4f2a661](4f2a661494))
* display passengers visually on train and at stations ([1599904](159990489f))
* dynamically calculate train cars based on max concurrent passengers ([9ea1553](9ea15535d1))
* enable prominent nav and fix layout on arcade page ([5c8c18c](5c8c18cbb8))
* enhance emoji picker with super powered magnifying glass and hide empty categories ([d8b4e42](d8b4e425bf))
* enhance passenger card UI with boarding status indicators ([4bbdabc](4bbdabc3b5))
* extend ground terrain to cover entire track area ([ee48417](ee48417abf))
* extend player customization to support all 4 players ([72f8dee](72f8dee183))
* extend railroad track to viewport edges ([eadd7da](eadd7da6db))
* extend track and tunnels to absolute viewport edges ([f7419bc](f7419bc6a0))
* implement smooth train exit with fade-out through right tunnel ([0176694](01766944f0))
* improve game availability logic and messaging ([9a3fa93](9a3fa93e53))
* increase landmark emoji size for better visibility ([0bcd7a3](0bcd7a30d4))
* integrate remaining game sound effects ([600bc35](600bc35bc3))
* integrate sound effects into game flow (countdown, answers, performance) ([8c3a855](8c3a855239))
* make Steam Sprint infinite mode ([32c3a35](32c3a35eab))
* make SVG span full viewport width for sprint mode ([7488bb3](7488bb3803))
* preserve track and passengers during route transitions ([f2e7165](f2e71657dc))
* redesign passenger cards with vintage train station aesthetic ([651bc21](651bc21583))
* skip countdown for train mode (sprint) ([65dafc9](65dafc9215))
* skip intro screen and start directly at game setup ([4b6888a](4b6888af05))
* sync URL with selected game mode ([3920bba](3920bbad33))
* UI polish for Sprint mode (viewport, backgrounds, data attributes) ([90ad789](90ad789ff1))
* use CSS transitions for smooth fullscreen player selection collapse ([3189832](31898328a3))
* wire player configuration through nav component hierarchy ([edfdd81](edfdd81227))
### Performance Improvements
* optimize React rendering with memoization and consolidated effects ([93cb070](93cb070ca5))
Problem: When multiple passengers were waiting at the same station and a car
arrived, they could all try to board the same car in the same game loop
iteration. This happened because currentBoardedPassengers was calculated once
at the start of each frame and didn't reflect passengers who boarded during
that same iteration.
Solution: Track which cars are assigned within each frame using a Set. Before
assigning a passenger to a car, check both:
1. currentBoardedPassengers (passengers from previous frames)
2. carsAssignedThisFrame (passengers assigned this frame)
This ensures only one passenger boards per car per frame, preventing the bug
where passengers get left behind at stations because the game thinks they've
already boarded when they haven't.
Tests: Added 6 comprehensive boarding logic tests that successfully reproduce
and verify the fix for various edge cases including:
- Single passenger boarding
- Multiple passengers with enough cars
- Fast-moving train scenarios
- Passenger left behind scenarios
- Single car with multiple passengers
- All passengers boarding before train passes
All tests pass (6/6).
Problem: Route completion threshold was recalculated every frame based on
current passengers. When passengers were auto-regenerated mid-route (after
all delivered), the maxCars value could change, shifting the threshold and
potentially causing the train to never cross it properly.
Solution:
- Store route exit threshold in a ref when route starts
- Only update threshold at route completion for next route
- Threshold remains stable throughout entire route even when passengers regenerate
This ensures trains always complete routes when reaching the exit threshold,
preventing situations where players get stuck answering problems after train
has disappeared.
- Track displayRouteRef to identify which route's passengers are shown
- Only update passengers when train resets (< 0) OR same route and in middle of track (10-90%)
- Exclude start/end transition zones to prevent premature passenger updates
- Add comprehensive unit tests (11 tests) covering edge cases:
- New passengers at position 0 with old route
- Passengers regenerated at 5% position
- Rapid route increment with position oscillation
- Multiple rapid gameplay updates during same route
- All 44 hook tests pass
- Use bezier curve paths instead of polylines for rails to eliminate jaggies on sharp turns
- Sample rail waypoints densely (every 2px) with gentle control points (0.33)
- Use longer lookahead distance (8px) for smoother perpendicular angle calculation
- Implement seeded random number generator for consistent tracks per route
- Each route generates a unique but deterministic track layout
The rails were rendered as polylines with points sampled at each tie position
(every 12 pixels). On sharp turns, the inside rail (smaller radius) didn't
have enough points to maintain smoothness, creating visible jaggies.
Solution: Separate tie generation from rail point generation. Ties still use
12px spacing (looks good), but rails now sample at 3px intervals (4x denser).
This provides enough points for smooth curves even on the inside rail of
sharp turns, while keeping tie density reasonable.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
The useSteamJourney hook was still using hard-coded MAX_CARS = 5 for:
- Checking which cars should board passengers
- Checking which cars should deliver passengers
- Calculating when entire train exits (route completion)
This caused the game to wait for a 5-car train to exit even when there were
fewer passengers, making players answer problems well after the last visible
car had exited.
Now dynamically calculates maxCars in the game loop using the same
calculateMaxConcurrentPassengers() utility, ensuring route completion
happens as soon as the actual last car exits.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Instead of hard-coding 5 train cars, now calculate the number of cars needed
based on the maximum number of passengers that will be on the train at any
given moment during the route.
For example: if 8 total passengers exist, but only 4 board at the start, all
get off halfway, then the remaining 4 board and ride to the end, we only need
4 cars (not 8).
Added calculateMaxConcurrentPassengers() utility that:
- Tracks boarding/delivery events by station position
- Sorts events to handle same-station boarding/delivery correctly
- Returns the peak concurrent passenger count
Updated SteamTrainJourney to calculate maxCars dynamically using this utility.
Updated all hooks and tests to use required maxCars/carSpacing parameters.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Train mode now starts immediately when clicking "Start Your Race!" button,
bypassing the 3-2-1-GO countdown. Other game modes (practice, survival) still
show the countdown as expected.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Previously, passengers would update as soon as all cars exited (at 97%+),
causing new passengers to briefly appear on the old track before it changed.
Now passengers only update when:
1. Train resets to start position (< 0) - track has changed, OR
2. Same passengers (same route gameplay updates like boarding/delivering)
This eliminates the ephemeral passengers showing up after the last car
fades out but before the new track is displayed.
Updated test to verify passengers don't change until train resets.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Fix the actual bug: passengers at stations and in passenger list were
switching to the new route once the locomotive exited, but before the
last train car exited.
Root cause: RailroadTrackPath was using state.passengers directly instead
of displayPassengers, which has transition logic to delay the switch until
all cars have exited.
The previous commit added the transition logic to useTrackManagement, but
RailroadTrackPath wasn't using the displayPassengers output - it was still
reading state.passengers directly.
Changes:
- SteamTrainJourney: Pass displayPassengers to RailroadTrackPath instead
of state.passengers
Note: usePassengerAnimations correctly continues to use state.passengers
for immediate animation triggering. boardedPassengers and
nonDeliveredPassengers already use displayPassengers correctly.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Fix bug where new route passengers would appear on train cars before
all cars from the previous route had exited through the tunnel.
The issue occurred because passengers were switched when trainPosition < 0
(locomotive exits), but train cars trail behind by up to 35% (5 cars × 7%
spacing). This caused new passengers to briefly appear on the old cars that
were still fading out (positions 65-97%).
Solution: Calculate the last car's position and only switch passengers when:
1. Train has reset to start position (trainPosition < 0), OR
2. All cars have fully faded out (lastCarPosition >= 97%)
Changes:
- useTrackManagement: Added maxCars and carSpacing parameters
- Updated passenger display logic to check lastCarPosition >= fadeOutEnd
- SteamTrainJourney: Pass maxCars and carSpacing from useTrainTransforms
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Extract game HUD elements (route info, time, pressure gauge, passenger list,
question display) into a separate GameHUD component for better maintainability.
- Created GameHUD.tsx (190 lines)
- Reduced SteamTrainJourney.tsx from 412 to 283 lines (-129 lines, 31.3%)
- Preserved all HUD elements and functionality exactly
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Extract train rendering (locomotive, cars, passenger animations) into
a separate TrainAndCars component for better maintainability.
- Created TrainAndCars.tsx (217 lines)
- Reduced SteamTrainJourney.tsx from 546 to 412 lines (-134 lines, 24.5%)
- Preserved all train elements and animations exactly
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Extract track rendering (ties, rails, path, landmarks, stations) into
a separate RailroadTrackPath component for better maintainability.
- Created RailroadTrackPath.tsx (192 lines)
- Reduced SteamTrainJourney.tsx from 687 to 546 lines (-141 lines, 20.5%)
- Preserved all track elements and passenger rendering exactly
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Extract terrain background rendering (ground, mountains, tunnels) into
a separate TrainTerrainBackground component for better maintainability.
- Created TrainTerrainBackground.tsx (203 lines)
- Reduced SteamTrainJourney.tsx from 857 to 687 lines (-170 lines, 19.8%)
- Preserved all visual elements and functionality exactly
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Create dedicated hook for track generation and positioning logic
- Move 115+ lines of track/landmark/passenger display management to useTrackManagement.ts
- Consolidates track generation, ties/rails, station positions, landmarks, and passenger display transitions
- Reduce SteamTrainJourney.tsx from 959 to 857 lines (102 lines removed)
- Preserve all functionality exactly - no behavioral changes
Benefits:
- Centralizes all track-related state management
- Handles route transition logic in one place
- Makes track generation logic easier to test
- Improves overall code organization
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Create dedicated hook for train position and car transform calculations
- Move 71 lines of transform logic to useTrainTransforms.ts
- Extract train position useEffect, trainCars useMemo, and locomotiveOpacity useMemo
- Reduce SteamTrainJourney.tsx from 1023 to 959 lines (64 lines removed)
- Preserve all functionality exactly - no behavioral changes
Benefits:
- Separates transform calculations from presentation logic
- Makes train physics calculations easier to test
- Improves code organization and readability
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Remove duplicate ref declaration that was causing compilation error
- Use existing previousPassengersRef initialized with state.passengers
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Store pending track data and only apply when train resets to beginning
- Preserve passenger list display until entire train exits
- Prevent visual jumps by keeping old route data visible during fade-out
- Track transitions now seamless: old track/passengers persist until trainPosition < 0
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Previously, passengers would board/disembark when the locomotive reached their
station, which was incorrect. Now:
**Boarding:**
- Passengers board when an EMPTY train car reaches their origin station
- Each passenger is assigned to the first available empty car (0-4)
- Car position calculated as: trainPosition - (carIndex + 1) * 7%
**Disembarking:**
- Passengers disembark when THEIR specific car reaches their destination
- Uses the passenger's position in the boardedPassengers array to find car index
- Each passenger's car position is independently checked against their destination
This creates more realistic train behavior where passengers interact with
individual train cars rather than just the locomotive.
Removed unused imports: findBoardablePassengers, findDeliverablePassengers
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Allow train position to exceed 100% so entire train can exit before route change
- Change route completion threshold from 100% to 135% (locomotive + 5 cars at 7% spacing)
- Add fade-out effect for locomotive and train cars between 92-97% position
- Symmetric with fade-in effect (3-8%) used for left tunnel entrance
- Prevents jarring snap-back when route changes mid-train
The train now smoothly fades out as it enters the right tunnel, with the route
only changing after the entire train (including all passenger cars) has fully
exited through the tunnel.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Memoize BoardingPassengerAnimation and DisembarkingPassengerAnimation with React.memo
- Memoize expensive calculations: train cars, filtered passengers, ground texture
- Consolidate boarding/disembarking useEffect hooks to reduce passenger array processing
- Wrap PassengerCard in React.memo to prevent unnecessary re-renders
- Add useMemo for boardedPassengers and nonDeliveredPassengers lists
These optimizations reduce unnecessary re-renders and recalculations during gameplay,
improving performance especially when multiple passengers are in transit.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Implement a complete passenger train car system with animated boarding
and disembarking using react-spring.
Train Car System:
- Each passenger gets their own train car (🚃) following the track
- Cars follow curved track with proper rotation and spacing (7%)
- Cars fade in as they emerge from tunnel to avoid visual pile-up
- Compact car sizing (65px) and passenger sizing (42px)
- Maximum 5 cars per train for performance
Boarding Animations:
- Smooth spring-animated transitions from station to train car
- Passengers fly from station platform to assigned car (800ms)
- Passengers hidden from station and car during animation
- Animated passenger tracked separately to avoid flickering
Disembarking Animations:
- Reverse animation from train car to destination station
- Green glow effect for delivered passengers
- Celebration animation plays after landing at station
- Smooth transition prevents "ghost" effect
Station Passenger Display:
- Positioned directly above station circle (30px offset)
- Compact 55px size for better visual balance
- Tight horizontal spacing (28px) when multiple waiting
- Passengers properly excluded during boarding/disembarking
Visual Improvements:
- Removed decorative rock/bush elements from mountains
- Cleaner mountain tunnel appearance
- Better layering of animations between stations and train
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Redesign passenger information cards to match classic Grand Central
Terminal style with compact, elegant vintage design.
- Vintage color scheme: sepia, gold accents, dark backgrounds
- Courier New monospace font for mechanical board feel
- Compact layout with FROM/TO route information
- Shows origin station (was missing before)
- Status badges: WAIT, BOARD, DLVRD
- Color-coded by state (waiting/aboard/urgent/delivered)
- Art Deco gold borders and styling
- Much smaller footprint while showing more info
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Update passenger generation to only create passengers whose destination
stations are ahead of their origin stations (higher track position).
This prevents passengers from being stranded waiting for backwards travel.
- Exclude final station as possible origin (no stations ahead)
- Filter destination stations to only those with position > origin
- Maintains 40% depot start probability for variety
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Standardize positioning for all bottom-aligned elements:
- Pressure gauge: bottom 10px (fixed, z-index 1000)
- Question display: bottom 40px (fixed, z-index 1000)
- Passenger list: bottom 220px (fixed, z-index 1000)
Changed passenger list from absolute to fixed positioning and adjusted
bottom spacing to sit above the question display without overlapping.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Expand ground layer to span full viewport width and extend from
the top of the track (y=120) to the bottom of the viewport (y=650).
Changes:
- Ground now starts at y=120 (above highest track point at ~160)
- Height increased from 200 to 530 pixels
- Added scattered rock/pebble texture across ground surface
- Enhanced surface gradient from 40 to 60 pixels for better depth
The entire railroad track now sits on realistic earth terrain.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Enhanced tunnel entrances with proper mountain scenery:
Mountains:
- Added triangular mountain peaks rising above tunnel entrances
- Gradient shading for depth and dimension
- Rocky texture with vertical crack details
- Green vegetation/bushes at mountain base
Tunnels:
- Stone brick archways with brown/tan coloring
- Brick texture pattern on arch rim
- Dark interior for depth
Ground:
- Brown earth terrain extending full viewport width
- Gradient shading for ground surface depth
- Positioned below tunnel entrances
Train now emerges from/enters proper mountain tunnels set into
realistic terrain.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Remove constraints preventing full-width rendering:
- Remove 8px horizontal padding from track container in sprint mode
- Remove maxWidth: 1400px constraint from SVG
- Change justifyContent to 'stretch' for sprint mode
- Remove borderRadius from steam-train-journey container
Now the railroad track SVG truly spans the entire browser viewport
width, with tunnel entrances at the absolute edges.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Corrected tunnel positioning based on actual viewBox coordinates:
- viewBox is "-50 -50 900 700" (x: -50 to 850, y: -50 to 650)
- Left mountain face now starts at x=-50 (absolute left edge)
- Right mountain face now ends at x=850 (absolute right edge)
- Both mountain faces extend full viewport height
- Track waypoints adjusted to span from left tunnel (x=20) to right tunnel (x=780)
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Extend track waypoints from x: -120 to x: 920 (beyond viewport)
- Add mountain face rectangles at absolute left and right edges
- Redesign tunnel entrances as proper mountain tunnels with:
- Gray stone mountain faces extending to viewport edges
- Dark tunnel interiors
- Arched stone openings
- Stone rim detail around arch
Train now truly emerges from and enters into mountain tunnels at
the viewport boundaries.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Modify track waypoints to span from left edge (x: -50) to right edge
(x: 850) of the viewport, creating a more expansive journey across
the full screen width.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Increase landmark size multiplier from 2.5x to 4.0x, making scenery
emojis more prominent and visually similar in scale to the player
avatar (96px default vs 70px player).
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>