Increased inactive heaven bead gap from 3pt to 8pt for better visual
balance with earth beads. Now positioned at 14pt from top vs
reckoning bar at 20pt, giving 6pt clearance.
This provides more proportional spacing compared to earth beads
while keeping heaven beads clearly above the reckoning bar.
Updated all example images to reflect the improved positioning.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
My previous attempt to match earth bead gaps exactly resulted in
inactive heaven beads appearing below the reckoning bar at 27pt
while the bar is at 20pt.
Fixed by:
- Positioning inactive heaven beads at bead-size/2 + 3pt = 9pt from top
- This places them clearly above the reckoning bar (at 20pt)
- Removed unused inactive-bead-gap variable
- Active heaven beads remain just above the bar as intended
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
The 'Check My Solution' and 'End Game' buttons were hidden because
they were inside the .sorting-controls div, which gets hidden when
the game starts.
Solution:
- Move action buttons outside .sorting-controls into new .sorting-game-actions div
- Show/hide the entire .sorting-game-actions container instead of individual buttons
- Add CSS styling for the new container
- Buttons now remain visible throughout sorting gameplay
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
The previous fix used a fixed 5pt gap for heaven beads while earth beads
used a calculated gap of (bead-size + bead-spacing) + 5pt = 21pt.
This fix:
- Adds inactive-bead-gap variable for consistency
- Makes inactive heaven beads use same gap calculation as earth beads
- Now both heaven and earth inactive beads have visually equal spacing
- Updated all example images to show the corrected equal spacing
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
Fix heaven bead positioning issue where inactive heaven beads appeared
too close to the reckoning bar. Now inactive heaven beads use the same
5pt gap as inactive earth beads for visual consistency.
Changes:
- Inactive heaven beads: moved from 5pt+bead-size/2 to bead-size/2+5pt gap
- Active heaven beads: fine-tuned to heaven-earth-gap-bead-size/2-1pt
- Updated example images to reflect corrected positioning
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
Transform README from simple PDF generator description to comprehensive
documentation highlighting interactive web flashcards, quiz modes,
sorting challenges, multiple output formats, APIs, and educational features.
Major additions:
- Interactive web flashcards with quiz modes and sorting challenges
- Multiple output formats (PDF, PNG, SVG, HTML)
- REST API and Node.js integration documentation
- Comprehensive test coverage details
- Enhanced examples and feature categorization
- Updated project structure reflecting actual codebase
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
Replace problematic overflow behavior where cards knocked off the end
would return to selection pool. Cards now shift left to fill gaps,
only returning excess cards to pool when truly necessary.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
Major UX improvement replacing inline challenge sections with professional modal dialogs:
**Modal System:**
- Clean challenge buttons with attractive call-to-action design
- Professional modal dialogs with smooth animations (fadeIn, slideIn)
- Full Fullscreen API support with cross-browser compatibility
- ESC key, outside click, and close button dismiss modals
- Mobile-responsive design with optimized sizing
**Quiz Integration:**
- Fixed critical bug where quiz ran behind modal (invisible)
- Moved all quiz elements (game, input, results) inside modal
- Updated JavaScript to work with modal structure
- Maintained all existing functionality and scoring systems
**Technical Implementation:**
- ModalManager class handles all modal functionality
- Cross-browser fullscreen support with fallbacks
- Responsive CSS Grid layout for challenge buttons
- Import compatibility fixes for both direct and module execution
**Benefits:**
- Cleaner main page (no cluttered challenge controls)
- Immersive fullscreen experience for distraction-free challenges
- Professional modern UI with smooth transitions
- Better focus and attention on individual challenges
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Add permission for git restore command
- Required for git workflow during development
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Tests quiz HTML structure and control elements
- Validates JavaScript classes and methods
- Verifies default values and configuration
- Tests card count buttons and progress tracking
- Validates input parsing and scoring logic
- Checks countdown functionality and responsive design
- Tests accessibility features
- Covers various card count scenarios
Ensures interactive quiz features work correctly across different configurations.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add new web output format that generates a static HTML page with:
- Inline SVG abacus representations using existing Typst->SVG pipeline
- Hover functionality to reveal numerals on cards
- Responsive grid layout that works on desktop and mobile
- Print-friendly styles for offline practice
- Support for all existing configuration options (colors, shapes, etc.)
Usage: python3 src/generate.py --format web --range 1-10 --output cards.html
The web format reuses the existing visual generation code, ensuring
consistency with PDF/PNG/SVG outputs while providing an interactive
learning experience in the browser.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Remove test_reference_image_update_utility that was always skipped
- Remove --update-references option and make target that were unused
- Simplify reference image update process to manual deletion + test rerun
- Clean up documentation to reflect simpler approach
All tests now run without skipping. Reference updates are handled
by deleting old images and letting tests auto-generate new ones.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Fix empty array generation in Typst files (empty list now generates () not (,))
- Adjust range parsing test expectations to match actual behavior
- Fix visual test dimensions to use proper Typst units (2in vs 300px)
- Fix pytest configuration access for reference image updates
- Register pytest markers to eliminate warnings
- Adjust visual comparison thresholds for more reliable testing
All tests now pass successfully including visual regression tests.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add pytest integration to Makefile with new targets:
- make pytest: run all tests
- make pytest-fast: run unit tests only (skip slow integration tests)
- make pytest-visual: run visual regression tests only
- make pytest-cov: run tests with coverage reports
- make update-references: update visual test reference images
Update make install to use requirements.txt and reorganize help output
to clearly separate build, test, and setup targets.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
Implement pytest-based testing framework with:
- Unit tests for configuration parsing and core generation logic
- Visual regression tests using perceptual image hashing
- Fixtures and test configuration in conftest.py
- Test documentation and usage guide
Visual tests generate reference images and compare new output against them
to catch regressions while allowing for minor anti-aliasing differences.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
Add pytest and visual testing dependencies to requirements.txt:
- pytest>=7.0 for test framework
- pytest-cov>=4.0 for coverage reports
- pillow>=10.0 for image processing
- imagehash>=4.3 for visual regression testing
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Create templates/single-card.typ for individual card rendering
- Includes local copy of create-colored-numeral function
- Supports transparent backgrounds and exact card dimensions
- Used by PNG/SVG generation to avoid PDF intermediate
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Add 'make examples' to regenerate README images
- Add 'make verify-examples' for CI verification
- Create GitHub Action to verify examples are up to date
- Improve generate_examples.py with better error handling
- Add update-examples.sh convenience script
- Document development workflow in README
This ensures README examples always match the actual code output.
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Generate examples showing cutting guides and registration marks
- Add 'Printing Features' section to README
- Show full-page cutting guides for accurate card separation
- Include example with both cutting guides and registration marks
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Create generate_examples.py script to convert PDFs to PNGs
- Generate example images showcasing all major features
- Add image gallery to README showing:
- Basic soroban/numeral pairs
- Color schemes and colored numerals
- Different bead shapes
- Various layouts and options
- Include front/back examples for double-sided cards
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Document all new features (colors, shapes, scaling, skip counting)
- Add Node.js/TypeScript integration section
- Update command-line options documentation
- Include API usage examples
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Add TypeScript client for API consumption
- Add browser package setup for Typst.ts WASM
- Support for direct browser PDF generation
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Add bridge.py for clean JSON-based Python-Node communication
- Add optional FastAPI server for REST API access
- Include requirements for API server setup
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Add SorobanGenerator class with python-shell bridge
- No CLI arguments - clean TypeScript function calls
- Support for Express.js and Next.js integration
- Include comprehensive API documentation
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Add colored-numerals.yaml for place-value with colored text
- Add count-by-5s.yaml for skip counting example
- Demonstrate new features with ready-to-use configs
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Add --step flag to count by 2s, 5s, 10s, or any increment
- Update parse_range function to support step parameter
- Works with ranges to generate skip counting flashcards
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Add create-colored-numeral function for coloring digits
- Support place-value, heaven-earth, and alternating color schemes
- Numerals on back of cards now use same colors as beads on front
🤖 Generated with Claude Code
Co-Authored-By: Claude <noreply@anthropic.com>
- Implement horizontal and vertical cutting guides that extend across entire page
- Use subtle 50% gray lines (0.25pt) that won't be distracting if cut is slightly off
- Guides run through the gutter space between cards
- Automatically adjust to any grid layout (2x3, 3x3, 3x4, etc.)
- Controlled by existing --cut-marks flag
- Appear on both front and back sides for consistent cutting
The guides make it much easier to:
- Cut all cards to exactly the same size
- Make straight cuts across the entire page
- Maintain consistent spacing between cards
- Handle larger batches efficiently with a paper cutter
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Implement four color schemes: monochrome, place-value, heaven-earth, alternating
- Place-value: Different colors for ones (blue), tens (magenta), hundreds (orange), etc.
- Heaven-earth: Orange heaven beads, blue earth beads for visual distinction
- Alternating: Blue/green alternating columns for easier reading
- Add --color-scheme CLI flag and config support
- Create place-value-colors.yaml example config
Color coding helps students:
- Instantly recognize place values
- Distinguish between heaven and earth beads
- Reduce reading errors in multi-digit numbers
- Make learning more engaging and memorable
Default remains monochrome for printer-friendly output.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Support common layouts: 1, 2, 3, 4, 6, 8, 9, 10, 12, 15, 16, 18, 20, 24, 25, 30
- Add fallback logic for arbitrary card counts using square root calculation
- Remove panic on unsupported values - now handles any reasonable number
- Enable layouts like 18 cards (3x6) for larger batches
Users can now specify any cards-per-page value and get a reasonable
grid layout automatically calculated.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Wrap circles in a box for consistent top-left positioning
- All shapes now position from the same reference point
- Eliminates the bar appearing too high for circles only
Now all three shapes (diamond, square, circle) use the exact same
positioning logic with no special cases or exceptions.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- All shapes now use center-based positioning (no exceptions)
- Remove shape-specific adjustments for cleaner code
- Calculate bead positions using centers for all shapes
- Diamond and square shapes offset from center appropriately
This eliminates the complex conditional logic and makes the code
much cleaner and easier to maintain. All three shapes now follow
the same positioning rules.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Circles use center-based positioning (original Typst behavior)
- Diamonds and squares use top-edge positioning
- Add shape-specific y-coordinate adjustments for consistent alignment
- Ensure all active beads properly touch the reckoning bar
Each shape now positions correctly relative to the reckoning bar,
with circles using their natural center positioning and other shapes
using top-edge positioning.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Standardize bead positioning to use top edge as reference point
- Adjust circle positioning to match diamond and square alignment
- Ensure active beads properly touch the reckoning bar
- Fix issue where non-circle beads appeared too high
All bead shapes now align consistently with the reckoning bar,
with active beads properly positioned against it.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Add three bead shape options: diamond (default), circle, square
- Implement diamond shape as horizontally elongated rhombus (realistic)
- Add draw-bead function to handle all three shape types
- Update CLI with --bead-shape parameter
- Create circle-beads.yaml config for traditional round beads
Diamond shape is now the default as it more accurately represents
real soroban/abacus beads which are typically bi-conical or
rhombus-shaped when viewed from the side.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Clarify page ordering with detailed comments (fronts on odd, backs on even)
- Add PDF metadata for better document properties
- Improve qpdf linearization with object stream preservation
- Document duplex printing behavior in README
- Ensure consistent front/back pairing with explicit pagebreaks
The PDF now clearly alternates between soroban diagrams (odd pages)
and numerals (even pages) for reliable duplex printing with long-edge
binding.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Add hide-inactive-beads parameter to draw-soroban function
- Conditionally render beads based on active state
- Add --hide-inactive-beads CLI flag
- Create minimal-beads.yaml config example
- Support both display modes: full (with grayed inactive) and minimal (active only)
This allows users to choose between two common soroban display
conventions: showing all beads with inactive ones grayed out, or
showing only the active beads for a cleaner look.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Add DejaVuSans.ttf for main text
- Add DejaVuSans-Bold.ttf for emphasis
- Ensures PDF portability across systems
- No dependency on system fonts
DejaVu fonts are open source and freely redistributable.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Default target generates flashcards with linearization
- Install target for macOS dependencies (typst, qpdf)
- Sample generation target for all configurations
- Test target for quick validation
- Clean target to remove generated files
- Dependency checking before builds
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- default.yaml: Basic 0-9 configuration
- 0-99.yaml: Two-digit numbers with cut marks
- 3-column-fixed.yaml: Three-digit numbers with fixed columns
Each config includes paper size, margins, font settings, and
soroban display options.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Create generate.py with full CLI argument support
- Support YAML/JSON configuration files
- Implement number range parsing and shuffling
- Add font path configuration for bundled fonts
- Include PDF linearization with qpdf
- Add sample generation script for testing
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Implement draw-soroban function for rendering abacus beads
- Create flashcard layout with front/back support
- Add generate-flashcards main function for batch generation
- Support configurable layouts (6/8/9 cards per page)
- Include duplex printing alignment with mirrored backs
- Pure vector graphics using Typst drawing primitives
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Add .gitignore for Python, macOS, and generated files
- Add requirements.txt with PyYAML dependency
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>