Updated README.md and added CLAUDE.md

This commit is contained in:
2026-04-26 11:42:22 -04:00
parent 33c93ab86b
commit 16118dd958
2 changed files with 116 additions and 13 deletions
+78
View File
@@ -0,0 +1,78 @@
# CLAUDE.md
This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
## Commands
```bash
npm start # Dev server at http://localhost:3000
npm run build # Production build
npm test # Run tests (no test files currently exist)
```
Docker:
```bash
docker build -t ttrpg-initiative-tracker .
docker run -p 8080:80 --rm --name ttrpg-tracker-app ttrpg-initiative-tracker
```
The Dockerfile uses `NODE_OPTIONS=--openssl-legacy-provider npm run build` to work around an OpenSSL compatibility issue between Node 18 and react-scripts 5.
## Architecture
Single-page React app (Create React App) for DMs to manage TTRPG combat encounters with a real-time player display. The entire application — all components, hooks, Firebase init, and routing — lives in **`src/App.js`** (~2500 lines).
**Key dependencies:** React 18, Firebase SDK v10 (Firestore + anonymous auth), Tailwind CSS v3, lucide-react icons.
### Two App Modes (query-param routing)
- Default URL → `AdminView`: full DM interface (campaign/encounter/participant management)
- `?playerView=true` or `/display``DisplayView`: read-only player-facing view for a second monitor
### Firebase / Firestore
All app state lives in Firestore under `artifacts/{APP_ID}/public/data/`:
- `campaigns/` — campaign documents
- `campaigns/{id}/encounters/` — sub-collections with a `participants` array per encounter
- `activeDisplay/status` — single doc controlling what the player display shows
`APP_ID` defaults to `"ttrpg-initiative-tracker-default"` and can be overridden via `REACT_APP_TRACKER_APP_ID`.
All users authenticate anonymously (Firebase Anonymous Auth). If `window.__initial_auth_token` is set, a custom token is used instead.
Real-time updates use two custom hooks in App.js: `useFirestoreDocument(docPath)` and `useFirestoreCollection(collectionPath)`, both backed by `onSnapshot`.
### App.js Sections (in order)
1. Constants — `APP_VERSION`, `CONDITIONS` array, defaults
2. Firebase config — reads `REACT_APP_FIREBASE_*` env vars
3. Firestore path helpers — `getPath` object
4. Utility functions — `generateId()`, `rollD20()`, sort helpers
5. Custom hooks — `useFirestoreDocument`, `useFirestoreCollection`
6. Reusable UI — `Modal`, `ConfirmationModal`, `LoadingSpinner`, `ErrorDisplay`
7. Feature components — forms, managers, controls (see below)
8. `AdminView` (~line 1942) — root DM component
9. `DisplayView` (~line 2186) — root player component
10. `App` (~line 2426) — auth + routing
Major feature components: `CreateCampaignForm`, `CreateEncounterForm`, `EditParticipantModal`, `CharacterManager`, `ParticipantManager`, `InitiativeControls`, `EncounterManager`.
### Styling
Tailwind CSS with two custom font families configured in `tailwind.config.js`:
- `font-cinzel` — Cinzel (serif, used for headings)
- `font-garamond` — Alegreya Sans (default body font)
### Environment Variables
Copy `env.example` to `.env.local` and fill in Firebase credentials:
```
REACT_APP_FIREBASE_API_KEY
REACT_APP_FIREBASE_AUTH_DOMAIN
REACT_APP_FIREBASE_PROJECT_ID
REACT_APP_FIREBASE_STORAGE_BUCKET
REACT_APP_FIREBASE_MESSAGING_SENDER_ID
REACT_APP_FIREBASE_APP_ID
REACT_APP_TRACKER_APP_ID # optional, Firestore namespace
```
+38 -13
View File
@@ -1,4 +1,4 @@
# TTRPG Initiative Tracker (v0.2.1)
# TTRPG Initiative Tracker (v0.2.4)
![Here it is in use](images/in_use.png)
@@ -23,6 +23,7 @@ Have you tried it? Got feedback or questions? Discuss here: [https://discourse.d
* **Character Management:**
* Add and manage characters (player characters) within each campaign.
* Set default Max HP and default Initiative Modifier for each campaign character.
* The character list is collapsible to save screen space.
* **Encounter Management:**
* Create multiple encounters per campaign.
* Add characters from the campaign roster (with auto-rolled initiative based on their modifier and HP pre-filled from campaign defaults) or add custom monsters.
@@ -30,16 +31,33 @@ Have you tried it? Got feedback or questions? Discuss here: [https://discourse.d
* "Add All Campaign Characters" button for quickly populating encounters with initiative rolls.
* DM controls to start, pause/resume, advance turns, and end encounters.
* Visual feedback for rolled initiative when adding individual participants.
* Participants can be added mid-combat while the encounter is paused; the turn order recalculates on resume.
* **HP Tracking:**
* Apply damage or healing to any participant during combat directly from the DM view.
* When a participant reaches 0 HP they are automatically marked inactive and shown with a skull (☠️) icon.
* Healing a dead participant above 0 HP revives them and reactivates them in the turn order.
* **Death Save Tracking:**
* When a player character reaches 0 HP, three death save checkboxes appear in the DM view.
* Marking the third death save triggers a dissolve animation on the player display, then removes the participant from the encounter.
* **Conditions:**
* Apply any of the 15 standard D&D conditions to a participant: Blinded, Charmed, Deafened, Exhaustion, Frightened, Grappled, Incapacitated, Invisible, Paralyzed, Petrified, Poisoned, Prone, Restrained, Stunned, Unconscious.
* Active conditions are shown as emoji badges on both the DM view and the player display.
* Conditions can be toggled directly from the badge or from an expandable condition picker per participant.
* **Player Display:**
* A clean interface showing the current initiative order, participant HP (monster HP totals are hidden, only the bar is shown), and current turn.
* NPCs (monster-type) are visually distinct from hostile monsters.
* Displays custom campaign background if set.
* Shows a "Game Session Paused" message when no encounter is active or if the current encounter is paused by the DM.
* Player display is opened in a separate window via a button in the DM's header.
* A clean interface showing the current initiative order, round number, participant HP, and current turn.
* HP bars use color-coded thresholds: green (above half), yellow (quarter to half), red (below quarter), dark red (dead).
* Monster and NPC HP totals are hidden; only the color-coded bar is shown.
* Active conditions are displayed as emoji badges on each participant's card.
* Inactive participants (and dead ones) are greyed out with a grayscale filter.
* The current participant's card auto-scrolls into view when the turn advances.
* NPCs are visually distinct from hostile monsters, which are distinct from player characters.
* Displays a custom campaign background image if one is set.
* Shows a "Game Session Paused" message when no encounter is active, or "(Combat Paused)" when the DM pauses a running encounter.
* Player display is opened in a separate window via the "Open Player Window" button in the DM's header.
* **Real-time Updates:** Uses Firebase Firestore for real-time synchronization between DM actions and the player display.
* **Initiative Tie-Breaking:** DMs can drag-and-drop participants with tied initiative scores (before an encounter starts or while paused) to set a manual order.
* **Responsive Design:** Styled with Tailwind CSS.
* **Confirmation Modals:** Implemented for destructive actions like deleting campaigns, characters, encounters, or ending combat.
* **Confirmation Modals:** Used for destructive actions like deleting campaigns, characters, encounters, or ending combat.
## Tech Stack
@@ -70,16 +88,23 @@ The TTRPG Initiative Tracker is designed for Dungeon Masters to manage combat en
* Once participants are added and initiative is set, click "Start Encounter". This also automatically makes the encounter live on the Player Display.
* Use the "Pause" button to temporarily halt combat. While paused, you can adjust HP and re-order tied initiatives. Click "Resume" to continue.
* Use the "Next Turn" button (disabled when paused) to advance through the initiative order. The current combatant will be highlighted.
* Apply damage or healing to participants directly in the Admin View.
* Apply damage or healing to participants directly in the Admin View. Participants at 0 HP are automatically deactivated and marked with a skull icon. Healing them above 0 HP revives them.
* For player characters at 0 HP, track death saving throws using the three checkboxes that appear. Marking the third failure triggers a death animation on the player display and removes the participant.
* Apply or remove D&D conditions (Blinded, Charmed, Poisoned, etc.) using the ✨ button next to each participant. Active conditions appear as emoji badges on both the DM view and the player display.
* Mark participants as inactive (e.g., if knocked out) using the toggle next to their name.
* Click "End Encounter" (with confirmation) when combat is over. This also deactivates it from the Player Display.
2. **Player Display Window:**
* This window (opened by the DM via `/?playerView=true` URL) shows a simplified, header-less view of the active encounter.
* It displays the initiative order, current turn, round number, and participant HP (monster/NPC HP values are hidden, only the bar is shown).
* NPCs are styled with a muted gray background, distinct from hostile monsters (custom reddish-brown) and player characters (blueish).
* If a custom background URL was set for the campaign, it will be displayed.
* If no encounter is active on the Player Display, or if the current encounter is paused by the DM, it will show an appropriate message ("Game Session Paused" or "Combat Paused").
* This window (opened by the DM via the "Open Player Window" button, or accessed directly at `/display` or `/?playerView=true`) shows a simplified, header-less view of the active encounter.
* It displays the initiative order, current turn, round number, and participant HP bars. Monster/NPC HP totals are hidden; only the color-coded bar is shown. Player character HP is shown numerically.
* HP bars are color-coded: green (above 50%), yellow (2550%), red (below 25%), dark red (dead/0 HP).
* Active conditions are shown as emoji badges on each participant's card.
* The current participant's card automatically scrolls into view when the turn advances.
* NPCs are styled with a muted gray background, distinct from hostile monsters (reddish-brown) and player characters (dark blue/indigo).
* Dead and inactive participants are greyed out with a grayscale filter.
* When a player character's third death save is marked, a dissolve animation plays on the display before the participant is removed.
* If a custom background URL was set for the campaign, it will be displayed with a semi-transparent overlay behind the participant cards.
* If no encounter is active on the Player Display, it shows "Game Session Paused". If the current encounter is paused by the DM, it shows "(Combat Paused)".
This flow allows the DM to prepare and run encounters efficiently while providing a clear, real-time view for the players.