diff --git a/.claude-plugin/marketplace.json b/.claude-plugin/marketplace.json index 5321d23b..d8c09442 100644 --- a/.claude-plugin/marketplace.json +++ b/.claude-plugin/marketplace.json @@ -1,18 +1,18 @@ { - "name": "clawdnd", + "name": "worldos", "owner": { - "name": "100yenadmin" + "name": "electricsheephq" }, "metadata": { - "description": "ClawDnD — voice-acted D&D 5e campaigns with an AI Dungeon Master and a voiced AI companion.", - "homepage": "https://github.com/100yenadmin/ClawDnD" + "description": "WorldOS — simulate living worlds and play voice-acted D&D 5e campaigns inside them, with an AI Dungeon Master and a voiced AI companion.", + "homepage": "https://github.com/electricsheephq/WorldOS" }, "plugins": [ { - "name": "clawdnd", + "name": "worldos", "version": "1.0.0", "source": "./", - "description": "Adventure inside living, AI-generated D&D 5e worlds with a voiced AI companion — an AI DM generates epic stories live within persistent, canon-anchored worlds." + "description": "WorldOS — simulate living, AI-generated worlds and play epic D&D 5e inside them, with a voiced AI companion and an AI DM running stories within persistent, canon-anchored worlds." } ] } diff --git a/.claude-plugin/plugin.json b/.claude-plugin/plugin.json index f170ffa5..31fe7b8c 100644 --- a/.claude-plugin/plugin.json +++ b/.claude-plugin/plugin.json @@ -1,11 +1,11 @@ { - "name": "clawdnd", + "name": "worldos", "version": "1.0.2", - "description": "Adventure inside living, AI-generated D&D 5e worlds with a voiced AI companion — an AI DM generates epic stories live within persistent, canon-anchored worlds; deterministic 5e rules, searchable memory, fully voice-acted.", + "description": "WorldOS — simulate living, AI-generated worlds and play epic D&D 5e inside them. An AI DM generates stories live within persistent, canon-anchored worlds; deterministic 5e rules, searchable memory, a voiced AI companion, fully voice-acted.", "author": { - "name": "100yenadmin" + "name": "electricsheephq" }, - "repository": "https://github.com/100yenadmin/ClawDnD", + "repository": "https://github.com/electricsheephq/WorldOS", "license": "MIT", "keywords": [ "dnd", @@ -21,5 +21,5 @@ "claude-code", "mcp" ], - "homepage": "https://github.com/100yenadmin/ClawDnD#readme" + "homepage": "https://github.com/electricsheephq/WorldOS#readme" } diff --git a/.github/workflows/macos-swift.yml b/.github/workflows/macos-swift.yml index 8333635a..0b5839f5 100644 --- a/.github/workflows/macos-swift.yml +++ b/.github/workflows/macos-swift.yml @@ -7,7 +7,7 @@ on: - macos/swift-ci paths: - ".github/workflows/*.yml" - - "macos/ClawDnDApp/**" + - "macos/WorldOSApp/**" - "script/build_and_run.sh" - "scripts/*.sh" - "scripts/**/*.sh" @@ -17,7 +17,7 @@ on: - macos/native-app-shell paths: - ".github/workflows/*.yml" - - "macos/ClawDnDApp/**" + - "macos/WorldOSApp/**" - "script/build_and_run.sh" - "scripts/*.sh" - "scripts/**/*.sh" @@ -38,4 +38,4 @@ jobs: find scripts -type f -name "*.sh" -print0 | xargs -0 -n 1 bash -n - name: Build native app - run: swift build --package-path macos/ClawDnDApp + run: swift build --package-path macos/WorldOSApp diff --git a/.gitignore b/.gitignore index eb0f06e9..6e0c3f50 100644 --- a/.gitignore +++ b/.gitignore @@ -47,8 +47,8 @@ venv/ # Native macOS app build outputs /dist/ -/macos/ClawDnDApp/.build/ -/macos/ClawDnDApp/.swiftpm/ +/macos/WorldOSApp/.build/ +/macos/WorldOSApp/.swiftpm/ # TTS models / audio caches (large, regenerated locally) *.onnx diff --git a/CHANGELOG.md b/CHANGELOG.md index 7c41f742..141e389f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,8 +1,8 @@ # Changelog -All notable changes to ClawDnD are documented here. +All notable changes to WorldOS (formerly ClawDnD) are documented here. [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) format. -ClawDnD's code is MIT; world seeds are licensed separately (see `content/worlds/README.md`). +WorldOS's code is MIT; world seeds are licensed separately (see `content/worlds/README.md`). --- diff --git a/CLAUDE.md b/CLAUDE.md index f545085d..992144dc 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -1,17 +1,26 @@ -# ClawDnD — working guide (read before editing/running) +# WorldOS — working guide (read before editing/running) -A post-Baldur's-Gate-3 D&D 5e living-world game shipped as a Claude Code plugin, with a -native macOS app. This file is auto-loaded when working in the repo — it exists so we never -again run the wrong UI or work from the wrong checkout (both have bitten us). +WorldOS simulates living, AI-generated worlds and lets you play epic D&D 5e inside them — +shipped as a Claude Code plugin, with a native macOS app. The flagship world is a +post-Baldur's-Gate-3 5e living world. This file is auto-loaded when working in the repo — it +exists so we never again run the wrong UI or work from the wrong checkout (both have bitten us). + +> Naming note: the project was renamed `ClawDnD` → `WorldOS` (GitHub repo +> `100yenadmin/ClawDnD` → `electricsheephq/WorldOS`; the old URL redirects). The product name is +> now **WorldOS**. Some lower-level identifiers are still being migrated in later PRs and remain +> `clawdnd`-named on purpose: the MCP servers (`clawdnd-engine`, `clawdnd-rules`, `clawdnd-voice`, +> `clawdnd-player`), the `CLAWDND_*` env vars, and the `dev.clawdnd.app` bundle id. Treat those as +> the live wire/contract names until their dedicated rename PRs land — don't "fix" them ad hoc. ## Which checkout am I in? - **Canonical working checkout: `/Users/lume/ClawDnD-val`** — it tracks GitHub - `100yenadmin/ClawDnD` `main`. Edit, run, commit, and verify here. + `electricsheephq/WorldOS` `main`. Edit, run, commit, and verify here. (The directory name is + kept as-is for now; only the product was renamed.) - **`/Volumes/LEXAR/repos/ClawDnD-val` and `/Volumes/LEXAR/repos/ClawDnD` are DEPRECATED** (the pre-2026-05-28 location). Do not edit or run from them. They're kept only as fast-forwarded read-only mirrors and are guarded so an accidental run still serves local code. -- If `git remote -v` shows `100yenadmin/ClawDnD` but your `pwd` is under `/Volumes/LEXAR/…`, - you're on the deprecated mirror — switch to `/Users/lume/ClawDnD-val`. +- If your `pwd` is under `/Volumes/LEXAR/…`, you're on the deprecated mirror — switch to + `/Users/lume/ClawDnD-val`. - The Claude Code **preview tool roots at the LEXAR path**, so don't trust `preview_start` blindly — run the viewer yourself (below) from the canonical checkout, or confirm the served code is current (root must 302→`/openworlds/`; `chrome.jsx` must have zero `traffic-lights`). @@ -19,7 +28,8 @@ again run the wrong UI or work from the wrong checkout (both have bitten us). ## The UI is OpenWorlds — NOT the root dashboard - The real, current UI is the **OpenWorlds React SPA at `/openworlds/`** (`viewer/openworlds/*.jsx`, in-browser Babel, no build step), served by `viewer/server.py`. - The native app `dist/ClawDnD.app` loads `/openworlds/`. + The native app `dist/WorldOS.app` loads `/openworlds/`. ("OpenWorlds" is the SPA codename — + a sub-component of WorldOS — and stays.) - **`http://127.0.0.1:/` (the root) is the LEGACY pre-OpenWorlds dashboard** — it now redirects to `/openworlds/`. Never treat the root, `viewer/index.html`, or `dashboard.html` as the current UI. Always verify at `/openworlds/`. @@ -31,6 +41,7 @@ CLAWDND_STATE_DIR= CLAWDND_REPO_ROOT="$PWD" \ # Pass "" for the campaign to just set a port (a bare numeric arg is read as a CAMPAIGN id, # not the port, and silently binds the default 8765). Then open /openworlds/ — not the root. ``` +(The `CLAWDND_*` env vars are the current names; a later PR adds `WORLDOS_*` aliases.) Headless capture: `qa/owshot.sh ` (fresh Chrome profile → no stale cache). The viewer sends `Cache-Control: no-store` and version-stamps the index scripts, but a long-lived browser profile can still hold an old copy — use a fresh profile when in doubt. @@ -65,8 +76,8 @@ full sweep when the main disk is tight; engine single-process locally is light. An agent resuming this project should read in this order, then consult the rest by need: 1. **`CLAUDE.md`** (this file) — checkout/UI/run guardrails + this map. Auto-loaded. -2. **`ClawDnD-RUNBOOK.md`** — the compaction-resilience doc: architecture, invariants, dev/QA loops, lessons, work queue. READ FIRST after this. -3. **`ClawDnD-NORTH-STAR.md`** — *what "great" means* (the optimization target). The score is a **proxy** for the felt prestige-CRPG session; come here when score and gut disagree. +2. **`WorldOS-RUNBOOK.md`** — the compaction-resilience doc: architecture, invariants, dev/QA loops, lessons, work queue. READ FIRST after this. +3. **`WorldOS-NORTH-STAR.md`** — *what "great" means* (the optimization target). The score is a **proxy** for the felt prestige-CRPG session; come here when score and gut disagree. 4. **`qa/SCORECARD.md`** — the running results ledger (every scored run). 5. Latest **session runbook**: `/Volumes/LEXAR/Codex/session-notes//clawdnd-*/` (`implementation-notes.html` or `runbook.html`) — the in-flight day-log. Current sprint: `2026-05-27/clawdnd-1.0-autonomous-sprint/runbook.html`. diff --git a/LICENSE b/LICENSE index 143b01c1..90fd170b 100644 --- a/LICENSE +++ b/LICENSE @@ -1,6 +1,6 @@ MIT License -Copyright (c) 2026 100yenadmin +Copyright (c) 2026 electricsheephq Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal @@ -22,7 +22,7 @@ SOFTWARE. --- -NOTE: This MIT license covers ClawDnD's own source code. Bundled third-party +NOTE: This MIT license covers WorldOS's own source code. Bundled third-party data and content carry their own licenses — see THIRD_PARTY_NOTICES.md and data/srd/ATTRIBUTION.md. In particular, the System Reference Document (SRD 5.2) data is licensed under CC-BY-4.0, not MIT. diff --git a/README.md b/README.md index d7bdd5a0..ab4fb885 100644 --- a/README.md +++ b/README.md @@ -1,14 +1,14 @@ -# ClawDnD +# WorldOS -**Play full D&D 5e campaigns with an AI Dungeon Master *and* a voiced AI companion — fully voice-acted.** +**Simulate living worlds. Play epic D&D 5e inside them — with an AI Dungeon Master *and* a voiced AI companion, fully voice-acted.** -ClawDnD is a Claude Code plugin. You don't play *against* the AI; you go on an adventure *with* it. A Dungeon Master narrates the world and voices every NPC, and a companion party member adventures alongside you — with its own character sheet, personality, voice, and agency. Dice and rules are deterministic (never hallucinated), campaigns persist across sessions, and every line is spoken aloud. +WorldOS is a Claude Code plugin. It simulates persistent, canon-anchored worlds whose standing threads move on their own — and lets you drop in and *play* a full D&D 5e adventure inside them. You don't play *against* the AI; you go on an adventure *with* it. A Dungeon Master narrates the world and voices every NPC, and a companion party member adventures alongside you — with its own character sheet, personality, voice, and agency. Dice and rules are deterministic (never hallucinated), worlds and campaigns persist across sessions, and every line is spoken aloud. -> **Status:** **v1.0.1** ([Release](https://github.com/100yenadmin/ClawDnD/releases/tag/v1.0.1), 2026-05-28). Tier-1 **plus a living-world generative engine plus a native macOS desktop app (OpenWorlds)** — built and green in CI: **engine 1385/1385 ✓, viewer 90/90 ✓**, license-check clean. The full deterministic stack (dice, characters, combat with tactical zones / monster Multiattack / Parry reactions / end-of-turn repeat saves, full SRD 5.2.1 spellcasting, rests, inventory/economy, NPC memory + companion dossiers, encounters, persistence, voice) runs under an AI DM that **generates epic, mature, Baldur's-Gate-caliber stories live inside persistent, canon-anchored worlds** — grounded by on-demand lore lookup, a searchable campaign memory, chronology, standing threads that move on their own, and a 2,076-record canon roster for the Sword Coast (the seven BG3 origin heroes carry full companion-dossier seeds for the engine's living-world systems). QA-scored on a story-craft lens (≥4.3/5, prestige-fantasy). The OpenWorlds desktop app renders 14 polished screens (Launcher / Table / Combat / Map / Character / Inventory / Relations / Dialogue / Forge / Merchant / Bestiary / Journal / Acts / World Seed / Create / Settings), all data-bound to live read-models; the Merchant BUY and Forge Craft buttons relay structured `/move` intents to the DM during a live session. Tier 2 (OpenClaw companion fork) remains the optional gateway milestone. See the [issues](https://github.com/100yenadmin/ClawDnD/issues) for the roadmap. +> **Status:** **v1.0.1** ([Release](https://github.com/electricsheephq/WorldOS/releases/tag/v1.0.1), 2026-05-28). Tier-1 **plus a living-world generative engine plus a native macOS desktop app (OpenWorlds)** — built and green in CI: **engine 1385/1385 ✓, viewer 90/90 ✓**, license-check clean. The full deterministic stack (dice, characters, combat with tactical zones / monster Multiattack / Parry reactions / end-of-turn repeat saves, full SRD 5.2.1 spellcasting, rests, inventory/economy, NPC memory + companion dossiers, encounters, persistence, voice) runs under an AI DM that **generates epic, mature, Baldur's-Gate-caliber stories live inside persistent, canon-anchored worlds** — grounded by on-demand lore lookup, a searchable campaign memory, chronology, standing threads that move on their own, and a 2,076-record canon roster for the Sword Coast (the seven BG3 origin heroes carry full companion-dossier seeds for the engine's living-world systems). QA-scored on a story-craft lens (≥4.3/5, prestige-fantasy). The OpenWorlds desktop app renders 14 polished screens (Launcher / Table / Combat / Map / Character / Inventory / Relations / Dialogue / Forge / Merchant / Bestiary / Journal / Acts / World Seed / Create / Settings), all data-bound to live read-models; the Merchant BUY and Forge Craft buttons relay structured `/move` intents to the DM during a live session. Tier 2 (OpenClaw companion fork) remains the optional gateway milestone. See the [issues](https://github.com/electricsheephq/WorldOS/issues) for the roadmap. ## What makes it different -The closest existing tools each miss something: commercial AI-DMs treat voice as a bolt-on, voice-first tools are screen-watching overlays rather than full games, and the Claude-native D&D projects have no voice at all. ClawDnD is the unoccupied intersection: **Claude-native + plays the whole game + deterministic 5e rules + persistent campaigns + multi-character voice acting.** +The closest existing tools each miss something: commercial AI-DMs treat voice as a bolt-on, voice-first tools are screen-watching overlays rather than full games, and the Claude-native D&D projects have no voice at all. WorldOS is the unoccupied intersection: **Claude-native + a living-world simulation + plays the whole game + deterministic 5e rules + persistent worlds + multi-character voice acting.** ## Architecture @@ -57,7 +57,7 @@ The deterministic core runs in three Python MCP servers and is exercised by a fu Once installed, drive the game from Claude Code with these commands: -**Living worlds — the generative mode, ClawDnD at its best:** drop into a persistent world and the DM generates an epic, mature story *live* within its canon (real places, factions, history, and an era it stays true to), grounded by on-demand lore lookup, with the world's standing threads moving on their own — different every playthrough. +**Living worlds — the generative mode, WorldOS at its best:** drop into a persistent world and the DM generates an epic, mature story *live* within its canon (real places, factions, history, and an era it stays true to), grounded by on-demand lore lookup, with the world's standing threads moving on their own — different every playthrough. | Command | What it does | |---|---| @@ -71,7 +71,7 @@ Once installed, drive the game from Claude Code with these commands: | `/roll ` | Make a real, auditable engine roll (`/roll d20 advantage`, `/roll 2d6+3`). | | `/voice-toggle [on\|off]` | Switch spoken voice on or off — text-only fallback when off. | -You don't strictly need the commands: the **dungeon-master** skill activates whenever you ask to start or continue a ClawDnD adventure. The commands are just the front door. +You don't strictly need the commands: the **dungeon-master** skill activates whenever you ask to start or continue a WorldOS adventure. The commands are just the front door. ## Play in the dashboard @@ -80,10 +80,10 @@ The local viewer can be more than a window onto the game — it can be the surfa - **In Claude Code** — type your turns and the DM responds in chat. Use `/world-play [id]` (or just ask). - **In the dashboard** — play in your browser: you act through the on-screen **action palette** (**Say** to speak in-scene, **Do** to attempt something, **Continue**, the dice / skill / save / combat buttons, and click-to-travel), and a live AI DM responds beside it, turn by turn. -To play in the dashboard, **double-click `clawdnd-play.command`** (a Desktop shortcut is installed by `scripts/install-desktop-shortcut.sh`), or run it from a terminal: +To play in the dashboard, **double-click `worldos-play.command`** (a Desktop shortcut is installed by `scripts/install-desktop-shortcut.sh`), or run it from a terminal: ```bash -./clawdnd-play.command # default living world +./worldos-play.command # default living world scripts/play.sh sundered-reach # a specific world — see /world-list ``` @@ -91,7 +91,7 @@ What to expect: your browser opens to `http://127.0.0.1:8765/dashboard`, the DM The DM loop is **safety-capped** so it can't run away: a per-turn budget, a whole-session budget ceiling, and a hard turn cap — adjust them with `CLAWDND_PLAY_BUDGET`, `CLAWDND_PLAY_SESSION_BUDGET`, and `CLAWDND_PLAY_MAX_TURNS`. Press **Ctrl-C** (or close the window) to stop. -> Not to be confused with `clawdnd-dashboard.command`, the read-only **director's view** — it *watches* a game (live or a QA run) without an action palette. `clawdnd-play.command` is the one that lets you *play*. +> Not to be confused with `worldos-dashboard.command`, the read-only **director's view** — it *watches* a game (live or a QA run) without an action palette. `worldos-play.command` is the one that lets you *play*. ## Quick start — install, create a character, play your first session @@ -106,20 +106,21 @@ The DM loop is **safety-capped** so it can't run away: a per-turn budget, a whol Clone the repo and register it with Claude Code in a single step: ```bash -git clone https://github.com/100yenadmin/ClawDnD.git -cd ClawDnD +git clone https://github.com/electricsheephq/WorldOS.git +cd WorldOS ``` Then inside Claude Code, register the local marketplace and install the plugin: ``` /plugin marketplace add . -/plugin install clawdnd@clawdnd +/plugin install worldos@worldos ``` Claude Code reads `.claude-plugin/plugin.json` and `.mcp.json`, starts the three MCP servers (`clawdnd-engine`, `clawdnd-rules`, `clawdnd-voice`) via `uv`, and the plugin -is live for the session. +is live for the session. (Those MCP server ids keep the `clawdnd-` prefix for now; a later +release migrates them alongside the `CLAWDND_*` env vars.) ### 3. Create a character and begin @@ -153,7 +154,7 @@ Or start a scripted campaign: `/campaign-new [name]` then `/session-start [id]`. ```bash # Double-click the desktop shortcut (after scripts/install-desktop-shortcut.sh), or: -./clawdnd-play.command # default world (baldurs-gate) +./worldos-play.command # default world (baldurs-gate) scripts/play.sh sundered-reach # specific world ``` @@ -167,7 +168,7 @@ resolves each move through the engine and narrates the next beat live. script/build_and_run.sh # builds with Swift, ad-hoc signs, opens the app ``` -The app (`macos/ClawDnDApp/`) hosts the same read-model screens (atlas, party, quests, +The app (`macos/WorldOSApp/`) hosts the same read-model screens (atlas, party, quests, event feed, combat, portrait art) as live engine read-models. Requires macOS 13+ and `swift` in your PATH (Xcode Command Line Tools). @@ -187,11 +188,11 @@ Kokoro runs on-device; no API key needed. ElevenLabs can drop in later via ## Licensing -ClawDnD's own **code is MIT** (see `LICENSE`). It reuses only permissively-licensed components and ships the **CC-BY-4.0 SRD 5.2** for rules. See `THIRD_PARTY_NOTICES.md` and `data/srd/ATTRIBUTION.md`. +WorldOS's own **code is MIT** (see `LICENSE`). It reuses only permissively-licensed components and ships the **CC-BY-4.0 SRD 5.2** for rules. See `THIRD_PARTY_NOTICES.md` and `data/srd/ATTRIBUTION.md`. **World seeds** (`content/worlds/`) are a separate layer with their own licensing: -- **Original seeds** (e.g. *The Sundered Reach*) are original ClawDnD content, **CC-BY-4.0**, built on SRD primitives. -- **Universe seeds based on existing settings** (e.g. the *Unofficial Baldur's Gate 3+ Universe Seed*) are **unofficial, FREE fan content** — game rules under the **D&D Open Game License / CC-BY SRD**, and setting names/lore/characters under the **Wizards Fan Content Policy** (and, for Baldur's Gate 3 elements, used as unofficial fan content of Larian Studios). They are **not official, not endorsed**, and never sold. Each such seed ships a `LICENSE.md` carrying the required notice. The MIT license covers ClawDnD's code only — **it does not extend to the universe seeds**, which remain the property of their respective rights-holders and are used here strictly as free, unofficial Fan Content. +- **Original seeds** (e.g. *The Sundered Reach*) are original WorldOS content, **CC-BY-4.0**, built on SRD primitives. +- **Universe seeds based on existing settings** (e.g. the *Unofficial Baldur's Gate 3+ Universe Seed*) are **unofficial, FREE fan content** — game rules under the **D&D Open Game License / CC-BY SRD**, and setting names/lore/characters under the **Wizards Fan Content Policy** (and, for Baldur's Gate 3 elements, used as unofficial fan content of Larian Studios). They are **not official, not endorsed**, and never sold. Each such seed ships a `LICENSE.md` carrying the required notice. The MIT license covers WorldOS's code only — **it does not extend to the universe seeds**, which remain the property of their respective rights-holders and are used here strictly as free, unofficial Fan Content. A `_private/` path under each content area stays **gitignored** for material you don't intend to publish. diff --git a/THIRD_PARTY_NOTICES.md b/THIRD_PARTY_NOTICES.md index 50d7f2c8..6386ba99 100644 --- a/THIRD_PARTY_NOTICES.md +++ b/THIRD_PARTY_NOTICES.md @@ -1,7 +1,7 @@ # Third-Party Notices -ClawDnD's own source code is licensed under MIT (see `LICENSE`). This file -records third-party material that ClawDnD bundles, adapts, or depends on, and +WorldOS's own source code is licensed under MIT (see `LICENSE`). This file +records third-party material that WorldOS bundles, adapts, or depends on, and the licensing decisions behind them. ## Bundled data @@ -15,7 +15,7 @@ the licensing decisions behind them. ## Runtime dependencies (permissive, installed from PyPI via uv) -ClawDnD's MCP servers depend on these packages: +WorldOS's MCP servers depend on these packages: - **mcp** (MIT) — the Model Context Protocol SDK / FastMCP. - **pydantic** (MIT) — state-model validation. - **rapidfuzz** (MIT) — fuzzy matching for rules lookups. @@ -52,13 +52,13 @@ attacks, dice, travel, quests, camp, settlements, consumables, and coins. - **Authors in this subset:** Lorc, Delapouite, and Willdabeast. The imported SVGs were normalized only for presentation by removing the opaque -background rectangle so the app can tint them as local CSS masks. ClawDnD does +background rectangle so the app can tint them as local CSS masks. WorldOS does not vendor the full icon set and does not fetch icon assets from a network CDN. ## Structural references — learn-from only (NO code copied) -These projects informed ClawDnD's design. After verifying their licensing -(2026-05-22), we copy **no code** from any of them; ClawDnD's engine, rules, and +These projects informed WorldOS's design. After verifying their licensing +(2026-05-22), we copy **no code** from any of them; WorldOS's engine, rules, and voice code is a clean-room implementation from the SRD and our own D&D 5e knowledge. @@ -73,7 +73,7 @@ knowledge. - **heffrey78/dnd-mcp** — no declared license. Encounter / CR-difficulty logic referenced only; reimplemented from the SRD. - **Sstobo/Claude-Code-Game-Master** — CC-BY-NC-SA-4.0 (NonCommercial + - ShareAlike), incompatible with ClawDnD's MIT licensing. Architecture studied; + ShareAlike), incompatible with WorldOS's MIT licensing. Architecture studied; not copied. - **PinchOfData/claude-dungeon-master** — no declared license. DM persona/tone studied; not copied. @@ -81,7 +81,7 @@ knowledge. ## Content policy Published commercial **adventures** (e.g. WotC titles) are copyrighted and are -**never** redistributed in this repository. ClawDnD ships original and +**never** redistributed in this repository. WorldOS ships original and CC-licensed content, generates campaigns from SRD primitives, and supports *private, local* import of adventures the user legally owns (kept under a git-ignored directory and never committed). @@ -92,7 +92,7 @@ World seeds are a distinct content layer with their own licensing (the project's MIT license covers code only and does **not** extend to them). Each seed ships a `LICENSE.md`; the CI gate (`scripts/license_check.py`) requires it. -- **Original seeds** (e.g. *The Sundered Reach*) — original ClawDnD content under +- **Original seeds** (e.g. *The Sundered Reach*) — original WorldOS content under **CC-BY-4.0**, built on SRD primitives. Clean-room; no third-party setting IP. - **Universe seeds based on existing settings** (e.g. the *Unofficial Baldur's Gate 3+ Universe Seed*) — **FREE, unofficial Fan Content**, never sold: diff --git a/ClawDnD-NORTH-STAR.md b/WorldOS-NORTH-STAR.md similarity index 99% rename from ClawDnD-NORTH-STAR.md rename to WorldOS-NORTH-STAR.md index 5e68929a..71d60d08 100644 --- a/ClawDnD-NORTH-STAR.md +++ b/WorldOS-NORTH-STAR.md @@ -1,11 +1,11 @@ -# ClawDnD — NORTH STAR (READ FIRST, alongside the RUNBOOK) +# WorldOS — NORTH STAR (READ FIRST, alongside the RUNBOOK) > **This is the optimization target.** The RUNBOOK tells you *how to work* (invariants, dev/QA > loops, the file map). This doc tells you *what "great" means* — the thing the whole loop serves. > When a decision is ambiguous, when the score and your gut disagree, when you're about to add a > feature: come back here. The North Star is **more than a score.** The score is a proxy for it. > -> Read order on resume: `ClawDnD-RUNBOOK.md` → this file → `implementation-notes.html` → `qa/SCORECARD.md`. +> Read order on resume: `WorldOS-RUNBOOK.md` → this file → `implementation-notes.html` → `qa/SCORECARD.md`. > > Voice: confident, opinionated, builder's. Last updated 2026-05-28 (post-v1.0.1). > @@ -15,7 +15,7 @@ ## PART 1 — THE TRUE GOAL (beyond the score) -ClawDnD has **two deliverables, and they are inseparable:** +WorldOS has **two deliverables, and they are inseparable:** **(A) The felt prestige-CRPG session.** A player should finish a session feeling what they feel after a great night of Baldur's Gate 3 — *that mattered; that was mine; I want to know what happens diff --git a/ClawDnD-RUNBOOK.md b/WorldOS-RUNBOOK.md similarity index 95% rename from ClawDnD-RUNBOOK.md rename to WorldOS-RUNBOOK.md index 7dc885d7..e3c1fbf8 100644 --- a/ClawDnD-RUNBOOK.md +++ b/WorldOS-RUNBOOK.md @@ -1,11 +1,12 @@ -# ClawDnD — RUNBOOK (READ FIRST on resume) +# WorldOS — RUNBOOK (READ FIRST on resume) > **Before anything: confirm you are in the canonical checkout and know the right UI.** > `CLAUDE.md` (repo root, auto-loaded) is the hub — canonical checkout is -> `/Users/lume/ClawDnD-val` (== GitHub `100yenadmin/ClawDnD` main; the `/Volumes/LEXAR/…` +> `/Users/lume/ClawDnD-val` (== GitHub `electricsheephq/WorldOS` main; the `/Volumes/LEXAR/…` > copies are DEPRECATED), the UI is OpenWorlds at `/openworlds/` (the root is the legacy > dashboard), and it carries the full project map + read order. See also the auto-memory -> `clawdnd-canonical-setup`. +> `clawdnd-canonical-setup`. (Product renamed ClawDnD → WorldOS; the checkout dir keeps its +> `ClawDnD-val` name for now per issue #295/W0-F.) > **This is the compaction-resilience doc.** If you are an agent resuming this project > after a context reset, read this top-to-bottom before doing anything. It captures the @@ -21,13 +22,13 @@ > > Last updated: 2026-05-28 (post-v1.0.1). > -> **v1.0.1 ([Release](https://github.com/100yenadmin/ClawDnD/releases/tag/v1.0.1)):** Phase-4 action lanes complete — Merchant BUY and Forge Craft now relay structured `/move` intents during live play (Create was already wired to the bridge). The seven BG3 origin heroes carry full `companion_dossier` blocks (wound / wants / fears / values / approval / banter / camp prompts). Native-app reliability: build script prefers stable Developer ID signing when keychain ACL allows; `script/unblock_native_app.sh` is a one-shot helper for security-scanner re-evaluation hangs. `docs/SPARKLE_SETUP.md` is the 7-step path to auto-update on top of Developer ID. Engine **1385/1385 ✓**, viewer **90/90 ✓**, license-check clean. **Open gap (owner-only):** first-run Keychain "Always Allow" click on a Developer-ID-signed app to end "popup every rebuild" — or run `script/unblock_native_app.sh` once. +> **v1.0.1 ([Release](https://github.com/electricsheephq/WorldOS/releases/tag/v1.0.1)):** Phase-4 action lanes complete — Merchant BUY and Forge Craft now relay structured `/move` intents during live play (Create was already wired to the bridge). The seven BG3 origin heroes carry full `companion_dossier` blocks (wound / wants / fears / values / approval / banter / camp prompts). Native-app reliability: build script prefers stable Developer ID signing when keychain ACL allows; `script/unblock_native_app.sh` is a one-shot helper for security-scanner re-evaluation hangs. `docs/SPARKLE_SETUP.md` is the 7-step path to auto-update on top of Developer ID. Engine **1385/1385 ✓**, viewer **90/90 ✓**, license-check clean. **Open gap (owner-only):** first-run Keychain "Always Allow" click on a Developer-ID-signed app to end "popup every rebuild" — or run `script/unblock_native_app.sh` once. --- ## PROJECT -**ClawDnD** — a post-Baldur's-Gate-3, **living-world D&D 5e Claude Code plugin**. You don't +**WorldOS** — a post-Baldur's-Gate-3, **living-world D&D 5e Claude Code plugin**. You don't play *against* the AI; you adventure *with* it. An AI Dungeon Master narrates and voices every NPC; a voiced AI companion adventures alongside you with its own sheet and agency. @@ -358,7 +359,7 @@ The detailed queue below is now mostly HISTORICAL — read `implementation-notes ### NATIVE DESKTOP APP — the play path (IN SCOPE; was the sibling lane) The macOS/OpenWorlds Swift shell is now part of this lane (the old "another agent owns it, stay out" note is retired; those PRs #150/#182/#187/#190-192 are merged). The app -(`macos/ClawDnDApp/`, built by `script/build_and_run.sh run` → `dist/ClawDnD.app`) is a +(`macos/WorldOSApp/`, built by `script/build_and_run.sh run` → `dist/WorldOS.app`) is a WKWebView loading the **live worktree** viewer at `/openworlds/` — so a **viewer/JS change lands on app relaunch with NO Swift rebuild** (the swift build is a ~0.1s no-op). diff --git a/assets/icon/ClawDnD.icns b/assets/icon/WorldOS.icns similarity index 100% rename from assets/icon/ClawDnD.icns rename to assets/icon/WorldOS.icns diff --git a/macos/ClawDnDApp/Package.swift b/macos/WorldOSApp/Package.swift similarity index 56% rename from macos/ClawDnDApp/Package.swift rename to macos/WorldOSApp/Package.swift index 881e6fc1..a4d43e06 100644 --- a/macos/ClawDnDApp/Package.swift +++ b/macos/WorldOSApp/Package.swift @@ -3,14 +3,14 @@ import PackageDescription let package = Package( - name: "ClawDnDApp", + name: "WorldOSApp", platforms: [ .macOS(.v13) ], products: [ - .executable(name: "ClawDnDApp", targets: ["ClawDnDApp"]) + .executable(name: "WorldOSApp", targets: ["WorldOSApp"]) ], targets: [ - .executableTarget(name: "ClawDnDApp") + .executableTarget(name: "WorldOSApp") ] ) diff --git a/macos/ClawDnDApp/RELEASE_CHECKLIST.md b/macos/WorldOSApp/RELEASE_CHECKLIST.md similarity index 86% rename from macos/ClawDnDApp/RELEASE_CHECKLIST.md rename to macos/WorldOSApp/RELEASE_CHECKLIST.md index 16010b5f..e7bb4f15 100644 --- a/macos/ClawDnDApp/RELEASE_CHECKLIST.md +++ b/macos/WorldOSApp/RELEASE_CHECKLIST.md @@ -1,4 +1,4 @@ -# ClawDnD Native macOS Release Checklist +# WorldOS Native macOS Release Checklist The v0.3 macOS lane starts with a locally signed development app. Notarization is release-trust work after the local shell, provider bridge, and dashboard hosting @@ -14,8 +14,8 @@ are stable. ```bash security find-identity -p codesigning -v -codesign --verify --deep --strict dist/ClawDnD.app -spctl -a -vv dist/ClawDnD.app +codesign --verify --deep --strict dist/WorldOS.app +spctl -a -vv dist/WorldOS.app ``` The build script ad-hoc signs the local app bundle when `codesign` is available. diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/App/ClawDnDApp.swift b/macos/WorldOSApp/Sources/WorldOSApp/App/WorldOSApp.swift similarity index 99% rename from macos/ClawDnDApp/Sources/ClawDnDApp/App/ClawDnDApp.swift rename to macos/WorldOSApp/Sources/WorldOSApp/App/WorldOSApp.swift index e6a9378e..5edc91ef 100644 --- a/macos/ClawDnDApp/Sources/ClawDnDApp/App/ClawDnDApp.swift +++ b/macos/WorldOSApp/Sources/WorldOSApp/App/WorldOSApp.swift @@ -2,7 +2,7 @@ import AppKit import SwiftUI @main -struct ClawDnDApp: App { +struct WorldOSApp: App { @NSApplicationDelegateAdaptor(AppDelegate.self) private var appDelegate @Environment(\.openWindow) private var openWindow @StateObject private var processService = AppProcessService() diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Models/AppSection.swift b/macos/WorldOSApp/Sources/WorldOSApp/Models/AppSection.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Models/AppSection.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Models/AppSection.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Models/CampaignSummary.swift b/macos/WorldOSApp/Sources/WorldOSApp/Models/CampaignSummary.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Models/CampaignSummary.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Models/CampaignSummary.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Models/DependencyStatus.swift b/macos/WorldOSApp/Sources/WorldOSApp/Models/DependencyStatus.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Models/DependencyStatus.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Models/DependencyStatus.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Models/LocalEndpoint.swift b/macos/WorldOSApp/Sources/WorldOSApp/Models/LocalEndpoint.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Models/LocalEndpoint.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Models/LocalEndpoint.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Models/ProviderModels.swift b/macos/WorldOSApp/Sources/WorldOSApp/Models/ProviderModels.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Models/ProviderModels.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Models/ProviderModels.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/AppProcessService.swift b/macos/WorldOSApp/Sources/WorldOSApp/Services/AppProcessService.swift similarity index 98% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Services/AppProcessService.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Services/AppProcessService.swift index 393c2195..8af5f20c 100644 --- a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/AppProcessService.swift +++ b/macos/WorldOSApp/Sources/WorldOSApp/Services/AppProcessService.swift @@ -19,7 +19,7 @@ final class AppProcessService: ObservableObject { var diagnostics: String { """ - ClawDnD Native App Diagnostics + WorldOS Native App Diagnostics Viewer: \(viewerEndpoint?.url.absoluteString ?? "stopped") Viewer status: \(viewerEndpoint?.status.rawValue ?? "stopped") Active campaign: \(activeCampaignID ?? "none") @@ -58,7 +58,7 @@ final class AppProcessService: ObservableObject { ) throws -> URL { let repoURL = URL(fileURLWithPath: repoPath) guard RepositoryLocator.looksLikeRepo(repoURL) else { - try throwAndRecord("Repo path is not a ClawDnD checkout: \(repoPath)") + try throwAndRecord("Repo path is not a WorldOS checkout: \(repoPath)") } guard Shell.which("python3") != nil else { try throwAndRecord("python3 is missing. Install Python 3 before launching the viewer.") @@ -131,7 +131,7 @@ final class AppProcessService: ObservableObject { ) throws -> URL { let repoURL = URL(fileURLWithPath: repoPath) guard RepositoryLocator.looksLikeRepo(repoURL) else { - try throwAndRecord("Repo path is not a ClawDnD checkout: \(repoPath)") + try throwAndRecord("Repo path is not a WorldOS checkout: \(repoPath)") } guard let port = PortFinder.firstFreePort(startingAt: preferredPort) else { diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/CampaignStore.swift b/macos/WorldOSApp/Sources/WorldOSApp/Services/CampaignStore.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Services/CampaignStore.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Services/CampaignStore.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/DependencyChecker.swift b/macos/WorldOSApp/Sources/WorldOSApp/Services/DependencyChecker.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Services/DependencyChecker.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Services/DependencyChecker.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/Diagnostics.swift b/macos/WorldOSApp/Sources/WorldOSApp/Services/Diagnostics.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Services/Diagnostics.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Services/Diagnostics.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/PortFinder.swift b/macos/WorldOSApp/Sources/WorldOSApp/Services/PortFinder.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Services/PortFinder.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Services/PortFinder.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/ProviderAdapters.swift b/macos/WorldOSApp/Sources/WorldOSApp/Services/ProviderAdapters.swift similarity index 97% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Services/ProviderAdapters.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Services/ProviderAdapters.swift index 91c2a4ff..6683e72c 100644 --- a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/ProviderAdapters.swift +++ b/macos/WorldOSApp/Sources/WorldOSApp/Services/ProviderAdapters.swift @@ -120,8 +120,8 @@ struct CodexProvider: ProviderAdapter { kind: kind, availability: .configured, detail: configuredCommand.isEmpty - ? "Ready. Launches the checked-in Codex wrapper with the ClawDnD provider environment and player-facade-only tool surface." - : "Ready. Launches your configured Codex command with the ClawDnD provider environment and player-facade-only tool surface.", + ? "Ready. Launches the checked-in Codex wrapper with the WorldOS provider environment and player-facade-only tool surface." + : "Ready. Launches your configured Codex command with the WorldOS provider environment and player-facade-only tool surface.", detectedPath: configuredCommand.isEmpty ? wrapper.path : cli ) } @@ -188,7 +188,7 @@ struct OpenClawProvider: ProviderAdapter { return ProviderStatus( kind: kind, availability: .installed, - detail: "OpenClaw CLI found. Configure a local ClawDnD launch command before starting sessions.", + detail: "OpenClaw CLI found. Configure a local WorldOS launch command before starting sessions.", detectedPath: cli ) } @@ -210,7 +210,7 @@ struct OpenClawProvider: ProviderAdapter { return ProviderStatus( kind: kind, availability: .configured, - detail: "Configured. The app will launch your command with ClawDnD provider environment variables.", + detail: "Configured. The app will launch your command with WorldOS provider environment variables.", detectedPath: cli ) } diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/RepositoryLocator.swift b/macos/WorldOSApp/Sources/WorldOSApp/Services/RepositoryLocator.swift similarity index 96% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Services/RepositoryLocator.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Services/RepositoryLocator.swift index a159d04f..048007ea 100644 --- a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/RepositoryLocator.swift +++ b/macos/WorldOSApp/Sources/WorldOSApp/Services/RepositoryLocator.swift @@ -19,7 +19,7 @@ enum RepositoryLocator { } let homeRepo = FileManager.default.homeDirectoryForCurrentUser - .appendingPathComponent("repos/ClawDnD") + .appendingPathComponent("repos/WorldOS") if looksLikeRepo(homeRepo) { return homeRepo.path } diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Services/Shell.swift b/macos/WorldOSApp/Sources/WorldOSApp/Services/Shell.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Services/Shell.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Services/Shell.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/CampaignsView.swift b/macos/WorldOSApp/Sources/WorldOSApp/Views/CampaignsView.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Views/CampaignsView.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Views/CampaignsView.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/EmptyStateView.swift b/macos/WorldOSApp/Sources/WorldOSApp/Views/EmptyStateView.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Views/EmptyStateView.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Views/EmptyStateView.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/LogsView.swift b/macos/WorldOSApp/Sources/WorldOSApp/Views/LogsView.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Views/LogsView.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Views/LogsView.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/MonitorView.swift b/macos/WorldOSApp/Sources/WorldOSApp/Views/MonitorView.swift similarity index 100% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Views/MonitorView.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Views/MonitorView.swift diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/PlayView.swift b/macos/WorldOSApp/Sources/WorldOSApp/Views/PlayView.swift similarity index 99% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Views/PlayView.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Views/PlayView.swift index 333bcb8e..abd7267a 100644 --- a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/PlayView.swift +++ b/macos/WorldOSApp/Sources/WorldOSApp/Views/PlayView.swift @@ -26,7 +26,7 @@ struct PlayView: View { Divider() webSurface } - .alert("ClawDnD could not start", isPresented: alertBinding) { + .alert("WorldOS could not start", isPresented: alertBinding) { Button("OK", role: .cancel) {} } message: { Text(alertMessage ?? "") diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/ProvidersView.swift b/macos/WorldOSApp/Sources/WorldOSApp/Views/ProvidersView.swift similarity index 98% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Views/ProvidersView.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Views/ProvidersView.swift index 4d69c568..8e3784c1 100644 --- a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/ProvidersView.swift +++ b/macos/WorldOSApp/Sources/WorldOSApp/Views/ProvidersView.swift @@ -18,7 +18,7 @@ struct ProvidersView: View { VStack(alignment: .leading) { Text("Providers") .font(.title2.weight(.semibold)) - Text("Launch adapters can only start processes that speak through ClawDnD's existing engine/player paths.") + Text("Launch adapters can only start processes that speak through WorldOS's existing engine/player paths.") .foregroundStyle(.secondary) } Spacer() diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/RootView.swift b/macos/WorldOSApp/Sources/WorldOSApp/Views/RootView.swift similarity index 99% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Views/RootView.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Views/RootView.swift index bd7bf097..ebaee1f8 100644 --- a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/RootView.swift +++ b/macos/WorldOSApp/Sources/WorldOSApp/Views/RootView.swift @@ -541,7 +541,7 @@ struct SidebarView: View { .navigationSplitViewColumnWidth(min: 180, ideal: 210) .toolbar { ToolbarItem(placement: .principal) { - Text("ClawDnD") + Text("WorldOS") .font(.headline) } } diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/SettingsView.swift b/macos/WorldOSApp/Sources/WorldOSApp/Views/SettingsView.swift similarity index 97% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Views/SettingsView.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Views/SettingsView.swift index 46a4e0a6..c2657319 100644 --- a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/SettingsView.swift +++ b/macos/WorldOSApp/Sources/WorldOSApp/Views/SettingsView.swift @@ -82,15 +82,15 @@ struct SettingsView: View { let expanded = repoPath.trimmingCharacters(in: .whitespacesAndNewlines) as NSString let path = expanded.expandingTildeInPath guard !path.isEmpty else { - return "Choose a ClawDnD checkout folder." + return "Choose a WorldOS checkout folder." } guard path.hasPrefix("/") else { - return "Use a full path, for example /Volumes/LEXAR/repos/ClawDnD." + return "Use a full path, for example /Users/you/WorldOS." } guard RepositoryLocator.looksLikeRepo(URL(fileURLWithPath: path)) else { - return "This folder does not look like a ClawDnD checkout." + return "This folder does not look like a WorldOS checkout." } return nil diff --git a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/WebView.swift b/macos/WorldOSApp/Sources/WorldOSApp/Views/WebView.swift similarity index 97% rename from macos/ClawDnDApp/Sources/ClawDnDApp/Views/WebView.swift rename to macos/WorldOSApp/Sources/WorldOSApp/Views/WebView.swift index dd4ad971..e1a621df 100644 --- a/macos/ClawDnDApp/Sources/ClawDnDApp/Views/WebView.swift +++ b/macos/WorldOSApp/Sources/WorldOSApp/Views/WebView.swift @@ -188,18 +188,18 @@ struct WebView: NSViewRepresentable { private func send(_ reply: NativeBridgeReply) { let dictionary = reply.dictionary guard JSONSerialization.isValidJSONObject(dictionary) else { - NSLog("ClawDnD native bridge produced an invalid JSON reply: \(dictionary)") + NSLog("WorldOS native bridge produced an invalid JSON reply: \(dictionary)") return } do { let data = try JSONSerialization.data(withJSONObject: dictionary) guard let json = String(data: data, encoding: .utf8) else { - NSLog("ClawDnD native bridge failed to encode reply as UTF-8: \(dictionary)") + NSLog("WorldOS native bridge failed to encode reply as UTF-8: \(dictionary)") return } webView?.evaluateJavaScript("window.ClawDnDNative && window.ClawDnDNative._reply(\(json));") } catch { - NSLog("ClawDnD native bridge reply serialization failed: \(error); reply=\(dictionary)") + NSLog("WorldOS native bridge reply serialization failed: \(error); reply=\(dictionary)") } } } diff --git a/script/build_and_run.sh b/script/build_and_run.sh index 31bb206c..4ec0581f 100755 --- a/script/build_and_run.sh +++ b/script/build_and_run.sh @@ -2,13 +2,15 @@ set -euo pipefail MODE="${1:-run}" -APP_NAME="ClawDnDApp" -DISPLAY_NAME="ClawDnD" +APP_NAME="WorldOSApp" +DISPLAY_NAME="WorldOS" +# Bundle ID intentionally kept as dev.clawdnd.app: changing it orphans existing +# installs (no upgrade path). Revisit at v2.0 with a migration. See issue #295 (W0-B). BUNDLE_ID="dev.clawdnd.app" MIN_SYSTEM_VERSION="13.0" ROOT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)" -PACKAGE_DIR="$ROOT_DIR/macos/ClawDnDApp" +PACKAGE_DIR="$ROOT_DIR/macos/WorldOSApp" DIST_DIR="$ROOT_DIR/dist" APP_BUNDLE="$DIST_DIR/$DISPLAY_NAME.app" APP_CONTENTS="$APP_BUNDLE/Contents" @@ -37,10 +39,10 @@ build_bundle() { # App icon (the brass d20 + claw-scratch mark). Copy the prebuilt .icns into # Contents/Resources and reference it via CFBundleIconFile so Finder / Dock / # the title bar show a real icon instead of the generic executable placeholder. - local icon_src="$ROOT_DIR/assets/icon/ClawDnD.icns" + local icon_src="$ROOT_DIR/assets/icon/WorldOS.icns" if [ -f "$icon_src" ]; then mkdir -p "$APP_CONTENTS/Resources" - cp "$icon_src" "$APP_CONTENTS/Resources/ClawDnD.icns" + cp "$icon_src" "$APP_CONTENTS/Resources/WorldOS.icns" fi cat >"$INFO_PLIST" <CFBundlePackageType APPL CFBundleIconFile - ClawDnD + WorldOS CFBundleIconName - ClawDnD + WorldOS LSMinimumSystemVersion $MIN_SYSTEM_VERSION NSPrincipalClass diff --git a/scripts/install-desktop-shortcut.sh b/scripts/install-desktop-shortcut.sh index 17c8b3ee..a8ef8720 100755 --- a/scripts/install-desktop-shortcut.sh +++ b/scripts/install-desktop-shortcut.sh @@ -1,21 +1,21 @@ #!/usr/bin/env bash -# Install a double-click "ClawDnD Dashboard" shortcut + a clickable link on the +# Install a double-click "WorldOS Dashboard" shortcut + a clickable link on the # Desktop, so the owner can open the live play/test dashboard without the terminal. # Re-run any time (e.g. after moving the repo) to refresh the shortcut. set -uo pipefail REPO="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)" DESK="${HOME}/Desktop" URL="http://127.0.0.1:8765/dashboard" -CMD="$DESK/ClawDnD Dashboard.command" +CMD="$DESK/WorldOS Dashboard.command" # The double-clickable shortcut: runs the repo launcher (starts the viewer + opens # the browser at /dashboard). REPO is baked in at install time. cat > "$CMD" </dev/null + osascript -e 'display alert "WorldOS Dashboard" message "Could not find the launcher. Is the drive with the repo mounted ($REPO)?"' 2>/dev/null echo "Launcher not found: \$LAUNCH"; read -r -p "Press return to close…" _; exit 1 fi exec "\$LAUNCH" "\$@" @@ -23,13 +23,13 @@ EOF chmod +x "$CMD" # A clickable internet-shortcut "link" (opens the URL once the server is running). -cat > "$DESK/ClawDnD Dashboard.webloc" < "$DESK/WorldOS Dashboard.webloc" < URL$URL WEBLOC echo "Installed on your Desktop:" -echo " • 'ClawDnD Dashboard.command' — double-click: starts the viewer + opens $URL" -echo " • 'ClawDnD Dashboard.webloc' — clickable link to $URL (once the server is running)" +echo " • 'WorldOS Dashboard.command' — double-click: starts the viewer + opens $URL" +echo " • 'WorldOS Dashboard.webloc' — clickable link to $URL (once the server is running)" echo "(First double-click of the .command: right-click → Open to clear the macOS warning.)" diff --git a/scripts/launch_common.sh b/scripts/launch_common.sh index ee254696..a3385044 100644 --- a/scripts/launch_common.sh +++ b/scripts/launch_common.sh @@ -80,8 +80,8 @@ clawdnd_choose_port() { fi if [ "$explicit" = "1" ]; then echo "Port $requested is already in use." >&2 - echo "Close the existing ClawDnD window, or run with another port:" >&2 - echo " ./clawdnd-play.command baldurs-gate '' 8766" >&2 + echo "Close the existing WorldOS window, or run with another port:" >&2 + echo " ./worldos-play.command baldurs-gate '' 8766" >&2 return 1 fi for p in $(seq $((requested + 1)) $((requested + 40))); do diff --git a/clawdnd-dashboard.command b/worldos-dashboard.command similarity index 92% rename from clawdnd-dashboard.command rename to worldos-dashboard.command index 47d515f4..7afe8b94 100755 --- a/clawdnd-dashboard.command +++ b/worldos-dashboard.command @@ -1,5 +1,5 @@ #!/usr/bin/env bash -# ClawDnD dashboard — DOUBLE-CLICK this file to open the play/test view in your +# WorldOS dashboard — DOUBLE-CLICK this file to open the play/test view in your # browser (no terminal typing needed). It auto-watches the most recent QA run so you # can see tests as they happen. Optional arg: a run id (e.g. `duo1`) to watch a # specific run, or `play` to watch your own live ~/.clawdnd game instead. @@ -35,5 +35,5 @@ URL="http://127.0.0.1:$PORT/dashboard" ( sleep 1.2; (command -v open >/dev/null 2>&1 && open "$URL") \ || (command -v xdg-open >/dev/null 2>&1 && xdg-open "$URL") \ || echo "Open $URL in your browser." ) & -echo "ClawDnD dashboard → $URL (close this window to stop)" +echo "WorldOS dashboard → $URL (close this window to stop)" exec python3 viewer/server.py "" "$PORT" diff --git a/clawdnd-monitor.command b/worldos-monitor.command similarity index 95% rename from clawdnd-monitor.command rename to worldos-monitor.command index 1e12c838..55dc7211 100755 --- a/clawdnd-monitor.command +++ b/worldos-monitor.command @@ -1,5 +1,5 @@ #!/usr/bin/env bash -# ClawDnD — CAMPAIGN MONITOR. DOUBLE-CLICK this file to open a live page that shows EVERY +# WorldOS — CAMPAIGN MONITOR. DOUBLE-CLICK this file to open a live page that shows EVERY # campaign running — your own games AND every parallel QA test run — in one place, auto- # refreshing. Jump between them, watch how each is going at a glance (party, location, day, # scores). It is READ-ONLY: it only watches; it never changes a campaign. @@ -17,7 +17,7 @@ if [ -z "$PY" ]; then fi URL="http://127.0.0.1:${PORT}/monitor" -echo "ClawDnD campaign monitor → ${URL}" +echo "WorldOS campaign monitor → ${URL}" echo "(read-only; watches every play + QA campaign. Ctrl-C or close this window to stop.)" echo diff --git a/clawdnd-play.command b/worldos-play.command similarity index 88% rename from clawdnd-play.command rename to worldos-play.command index 7ee45c98..074ef285 100755 --- a/clawdnd-play.command +++ b/worldos-play.command @@ -1,5 +1,5 @@ #!/usr/bin/env bash -# Play ClawDnD in the dashboard — DOUBLE-CLICK this file to start a new adventure you +# Play WorldOS in the dashboard — DOUBLE-CLICK this file to start a new adventure you # play in your browser (no terminal typing needed). It opens the play dashboard and runs # a live AI Dungeon Master beside it: you act through the action palette (Say / Do / # Continue, dice & combat, click-to-travel) and the DM narrates, voices the cast, and @@ -8,15 +8,15 @@ # # Optional args (passed straight through): [world-id] [run-id] [port] [companion-spec] # e.g. open the file normally for the default world, or run from a terminal: -# ./clawdnd-play.command sundered-reach +# ./worldos-play.command sundered-reach # # PLAY WITH AI COMPANIONS (opt-in) — add a party of AI companions who adventure ALONGSIDE # you, each its own agent acting through the same move palette you do (it can disagree, # take the lead, even betray you). Name them with a 4th arg (or $CLAWDND_PLAY_COMPANIONS), # COMMA-separated Name:class:persona_file[:spell1|spell2|…]: -# ./clawdnd-play.command baldurs-gate '' 8765 \ +# ./worldos-play.command baldurs-gate '' 8765 \ # "Seraphine:cleric:qa/play_companion.txt:Cure Wounds|Guiding Bolt,Brogan:fighter:qa/play_companion.txt" -# or: CLAWDND_PLAY_COMPANIONS="Brogan:fighter:qa/play_companion.txt" ./clawdnd-play.command +# or: CLAWDND_PLAY_COMPANIONS="Brogan:fighter:qa/play_companion.txt" ./worldos-play.command # Companions multiply the live AI cost (each is its own `claude -p`), so they're OFF by # default — double-clicking this file is exactly today's solo play. With NO companion spec # this delegates straight to scripts/play.sh, byte-for-byte unchanged. @@ -29,7 +29,7 @@ cd "$(dirname "$0")" || exit 1 status=$? if [ "$status" -ne 0 ] && [ "$status" -ne 130 ]; then echo - echo "ClawDnD did not start cleanly (exit $status)." + echo "WorldOS did not start cleanly (exit $status)." echo "The message above should say what was missing or which port was busy." if [ -t 0 ]; then echo