{"id":48010132,"url":"https://github.com/hiibolt/sabi","last_synced_at":"2026-04-04T13:37:19.810Z","repository":{"id":175651455,"uuid":"654268318","full_name":"hiibolt/sabi","owner":"hiibolt","description":"Bevy-based Visual Novel game engine with a custom theatre-script like language with advanced customization features.","archived":false,"fork":false,"pushed_at":"2026-01-11T19:59:22.000Z","size":16266,"stargazers_count":15,"open_issues_count":0,"forks_count":2,"subscribers_count":1,"default_branch":"master","last_synced_at":"2026-03-01T19:47:32.537Z","etag":null,"topics":["bevy-engine","pest","rust","visual-novel"],"latest_commit_sha":null,"homepage":"","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"agpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/hiibolt.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2023-06-15T18:45:58.000Z","updated_at":"2026-02-14T05:39:37.000Z","dependencies_parsed_at":null,"dependency_job_id":"8e84ae38-6ea4-443a-a2f0-7f56dc2b5f3c","html_url":"https://github.com/hiibolt/sabi","commit_stats":null,"previous_names":["boltr6/requiem","hiibolt/requiem","hiibolt/sabi"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/hiibolt/sabi","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hiibolt%2Fsabi","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hiibolt%2Fsabi/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hiibolt%2Fsabi/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hiibolt%2Fsabi/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/hiibolt","download_url":"https://codeload.github.com/hiibolt/sabi/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hiibolt%2Fsabi/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":31402276,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-04T10:20:44.708Z","status":"ssl_error","status_checked_at":"2026-04-04T10:20:06.846Z","response_time":60,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["bevy-engine","pest","rust","visual-novel"],"created_at":"2026-04-04T13:37:17.765Z","updated_at":"2026-04-04T13:37:19.793Z","avatar_url":"https://github.com/hiibolt.png","language":"Rust","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Sabi\n\nSabi is a visual novel engine built on Rust and Bevy ECS. It provides a domain-specific scripting language with stage direction syntax, a modular character system with emotion-based sprites, and runtime asset management through Bevy's asset pipeline.\n\n![Rust](https://img.shields.io/badge/rust-%23000000.svg?style=for-the-badge\u0026logo=rust\u0026logoColor=white)\n![Bevy](https://img.shields.io/badge/bevy-2C2D33?style=for-the-badge\u0026logo=bevy\u0026logoColor=white)\n\n## Features\n\n**Scripting Language**\n- Pest-based parser with stage direction syntax inspired by theatrical scripts\n- Scene-based organization with named transitions\n- Expression evaluation supporting string concatenation and variable substitution\n- Inline emotion changes during dialogue\n\n**Actor System**\n- JSON-based character definitions with sprite mappings per emotion and outfit\n- Frame-based sprite sheet animations with configurable FPS\n- Character positioning system using percentage-based coordinates that scale with window size\n- Fade in/out and directional facing with automatic sprite flipping\n- Actor movement with interpolation between positions\n\n**Rendering**\n- ECS-based architecture separating character state from visual representation\n- Background management with transition support\n- Customizable GUI elements (textbox, namebox) with 9-slice and auto scaling\n- Text rendering with character-by-character reveal animation\n- History system tracking all dialogue and stage directions\n\n**Development Environment**\n- Nix flake for reproducible builds\n- Hot-reloadable assets during development\n- Six example projects demonstrating different features\n- Modular plugin architecture for extending functionality\n\n## Getting Started\n\n### Prerequisites\n- Rust toolchain (1.80+)\n- Cargo\n\n### Running Examples\n\n```bash\ncargo run --example basic_startup\ncargo run --example character_operations\ncargo run --example animation\ncargo run --example background\ncargo run --example ui\ncargo run --example infotext\n```\n\n### Using Nix\n```bash\nnix develop\ncargo run --example basic_startup\n```\n\n## Script Language\n\nSabi scripts use a `.sabi` extension and organize content into scenes with stage directions:\n\n```\nSCENE opening\n    (GUI textbox changes to \"TEXTBOX_DEFAULT\")\n    (Background changes to \"classroom_day\")\n    (Nayu appears center)\n    Nayu: \"This is dialogue.\"\n    Nayu: (happy) \"Emotions can change inline.\"\n    MC: \"Player character speaks like this.\"\n    (Nayu moves right)\n    (Nayu looks left)\n    (Nayu fade out)\n    (Scene \"next_scene\" begins)\nCURTAIN\n```\n\n### Supported Commands\n\n**Character Operations**\n- `(Character appears [position] [looking direction] [emotion])`\n- `(Character disappears)`\n- `(Character fade in/out)`\n- `(Character moves position)`\n- `(Character looks left/right)`\n\n**Positions**: `center`, `left`, `right`, `far left`, `far right`, `invisible left`, `invisible right`\n\n**Scene Management**\n- `(Scene \"scene_name\" begins)` - Jump to different scene\n- `(Background changes to \"background_id\")`\n- `(GUI element changes to \"sprite_id\" [sliced|auto])` - Customize textbox/namebox\n\n**Animations**\n- `(Animated \"animation_id\" appears position scale N)`\n- `(Animated \"animation_id\" fade in/out)`\n- `(Animated \"animation_id\" moves position)`\n- `(Animated \"animation_id\" looks left/right)`\n\n**Dialogue**\n- `Character: \"dialogue text\"` - Named character speaks\n- `Character: (emotion) \"dialogue\"` - Inline emotion change\n- `MC: \"dialogue\"` - Main character (substitutes player name)\n- `info: \"text\"` - Narrator/info text\n\n**Logging**\n- `{log \"debug message\"}` - Console output for development\n\n## Project Structure\n\n```\nsrc/\n├── actor/           # Character and animation controllers\n├── background/      # Background rendering system\n├── chat/            # Dialogue box and text animation\n├── compiler/        # Script parser and AST\n└── loader/          # Asset loaders for JSON and .sabi files\n\nassets/sabi/\n├── acts/            # Script files organized by chapter\n├── animations/      # Animation sprite sheets (JSON)\n├── backgrounds/     # Background images\n├── characters/      # Character sprites and configs\n├── fonts/           # Text rendering fonts\n└── ui/              # UI element sprites\n```\n\n## Integration\n\nAdd Sabi to your Bevy app:\n\n```rust\nuse sabi::*;\nuse bevy::prelude::*;\n\nfn main() {\n    App::new()\n        .add_plugins(DefaultPlugins)\n        .add_plugins(SabiPlugin)\n        .add_systems(Startup, setup)\n        .run();\n}\n\nfn setup(\n    mut commands: Commands,\n    mut msg_writer: MessageWriter\u003cSabiStart\u003e,\n    mut user_defined_constants: ResMut\u003cUserDefinedConstants\u003e,\n) {\n    user_defined_constants.playername = \"Player\".into();\n    commands.spawn(Camera2d::default());\n    msg_writer.write(SabiStart(ScriptId { \n        chapter: \"chapter1\".into(), \n        act: \"opening\".into() \n    }));\n}\n```\n\n## Architecture\n\nSabi uses Bevy's ECS with a plugin-based architecture:\n\n- **Compiler Plugin**: Parses `.sabi` scripts into an AST, evaluates expressions, manages scene transitions and game state\n- **Character Controller**: Spawns/despawns actors, handles movement interpolation, manages fade effects and sprite switching\n- **Chat Controller**: Renders dialogue boxes, implements text reveal animation, maintains conversation history\n- **Background Controller**: Loads and transitions between background images\n\nThe system uses Bevy's message passing for coordination between plugins and resource-based state management for the script execution cursor and character configurations.\n\n## Asset Configuration\n\n**Character Definition** (`character.json`):\n```json\n{\n  \"name\": \"Nayu\",\n  \"outfits\": {\n    \"uniform\": {\n      \"emotions\": {\n        \"neutral\": \"nayu_neutral.png\",\n        \"happy\": \"nayu_happy.png\",\n        \"concerned\": \"nayu_concerned.png\"\n      }\n    }\n  }\n}\n```\n\n**Animation Definition** (`animation.json`):\n```json\n{\n  \"name\": \"fire\",\n  \"spritesheet\": \"fire_sheet.png\",\n  \"frames\": 8,\n  \"fps\": 12,\n  \"frame_width\": 64,\n  \"frame_height\": 64\n}\n```\n\n## Current Limitations\n\n- No save/load system\n- Audio not implemented\n- No branching/choice system\n- Text input requires external implementation\n- Asset paths are hardcoded relative to `assets/sabi/`\n\n## License\n\nSee [LICENSE.md](LICENSE.md)\n\n## Credits\n\n- UI Panels by [BDragon1727](https://bdragon1727.itch.io/custom-border-and-panels-menu-all-part)\n- Fire animation by [Devkidd](https://devkidd.itch.io/pixel-fire-asset-pack)","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fhiibolt%2Fsabi","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fhiibolt%2Fsabi","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fhiibolt%2Fsabi/lists"}