Phase 2 complete
This commit is contained in:
155
TESTING_PHASE2.md
Normal file
155
TESTING_PHASE2.md
Normal file
@@ -0,0 +1,155 @@
|
||||
# Phase 2 Testing Guide
|
||||
|
||||
## 🎯 Quick Testing Steps
|
||||
|
||||
### 1. Start the Application
|
||||
```bash
|
||||
# Terminal 1 - Backend
|
||||
cd /home/aodhan/projects/apps/storyteller
|
||||
python -m uvicorn main:app --reload --port 8000
|
||||
|
||||
# Terminal 2 - Frontend
|
||||
cd frontend
|
||||
npm start
|
||||
```
|
||||
|
||||
### 2. Test Character Creation Wizard
|
||||
|
||||
1. **Open browser:** http://localhost:3000
|
||||
2. **Enter Session ID:** Type any session ID (e.g., "test-session-123")
|
||||
3. **Click "✨ Create Character (Wizard)"**
|
||||
4. **Step through wizard:**
|
||||
- Step 1: Enter name, select gender
|
||||
- Step 2: Add description and background
|
||||
- Step 3: Choose race and class (click cards)
|
||||
- Step 4: Select personality type
|
||||
- Step 5: Choose AI model
|
||||
- Step 6: Review and create
|
||||
|
||||
### 3. Test Character Profile Display
|
||||
|
||||
1. After creating character, check:
|
||||
- Profile badges appear (Race, Class, Personality)
|
||||
- Character info shows all details
|
||||
- Export button is visible
|
||||
|
||||
### 4. Test Export
|
||||
|
||||
1. Click "📥 Export" button in character view
|
||||
2. JSON file should download
|
||||
3. Open JSON to verify all profile data is present
|
||||
|
||||
### 5. Test Import
|
||||
|
||||
1. Create a new session or use existing
|
||||
2. Click "✨ Create Character (Wizard)"
|
||||
3. In Step 1, click "📥 Import from JSON"
|
||||
4. Select previously exported character
|
||||
5. Verify all fields are populated
|
||||
6. Complete wizard to create
|
||||
|
||||
### 6. Test Profile-Based LLM Prompts
|
||||
|
||||
1. Send a message as the character
|
||||
2. Check backend logs for generated system prompt
|
||||
3. Should include race, class, and personality traits
|
||||
|
||||
### 7. Test Backward Compatibility
|
||||
|
||||
1. Click "↓ Quick Create" toggle
|
||||
2. Fill in simple form (legacy mode)
|
||||
3. Create character without profile
|
||||
4. Character should work normally
|
||||
|
||||
## ✅ Expected Behavior
|
||||
|
||||
### Wizard
|
||||
- [x] Smooth step navigation
|
||||
- [x] Visual progress indicator
|
||||
- [x] Selection cards highlight when clicked
|
||||
- [x] Form validation (name required, description required)
|
||||
- [x] Import populates all fields
|
||||
- [x] Review shows complete summary
|
||||
|
||||
### Profile Display
|
||||
- [x] Badges show race, class, personality
|
||||
- [x] Character info section displays properly
|
||||
- [x] Export button functional
|
||||
|
||||
### Export/Import
|
||||
- [x] Export downloads valid JSON
|
||||
- [x] JSON includes version, timestamp, character data
|
||||
- [x] Import reads JSON correctly
|
||||
- [x] Imported character gets new ID
|
||||
|
||||
### LLM Integration
|
||||
- [x] System prompts include profile traits
|
||||
- [x] Legacy characters still work
|
||||
- [x] Profile-based prompts are coherent
|
||||
|
||||
## 🐛 Known Issues
|
||||
|
||||
### Fixed
|
||||
- ✅ Syntax error with escaped quotes in docstring (fixed)
|
||||
|
||||
### To Monitor
|
||||
- Webpack deprecation warnings (harmless, won't affect functionality)
|
||||
- Frontend hot reload may require manual refresh
|
||||
|
||||
## 🎮 Demo Session Test
|
||||
|
||||
Try the pre-configured demo:
|
||||
1. Click "🏹 Play as Willow (Elf Ranger)"
|
||||
2. Willow should have legacy profile (no structured profile)
|
||||
3. Create new character with wizard
|
||||
4. Compare the two in gameplay
|
||||
|
||||
## 📊 Profile Options to Test
|
||||
|
||||
### Races
|
||||
- [ ] Human
|
||||
- [ ] Elf
|
||||
- [ ] Dwarf
|
||||
- [ ] Orc
|
||||
- [ ] Halfling
|
||||
|
||||
### Classes
|
||||
- [ ] Warrior
|
||||
- [ ] Wizard
|
||||
- [ ] Cleric
|
||||
- [ ] Archer
|
||||
- [ ] Rogue
|
||||
|
||||
### Personalities
|
||||
- [ ] Friendly
|
||||
- [ ] Serious
|
||||
- [ ] Doubtful
|
||||
- [ ] Measured
|
||||
|
||||
### Combinations to Try
|
||||
- Elf Wizard (Measured) - Classic magic user
|
||||
- Dwarf Warrior (Serious) - Traditional tank
|
||||
- Halfling Rogue (Friendly) - Lovable trickster
|
||||
- Orc Cleric (Doubtful) - Interesting contrast
|
||||
- Human Archer (Measured) - Balanced ranger
|
||||
|
||||
## 🔍 What to Check in Backend Logs
|
||||
|
||||
When character sends message, look for system prompt like:
|
||||
```
|
||||
You are [Name], a [gender] [race] [class]. [Description]
|
||||
[Race traits] [Class traits] [Personality traits]
|
||||
Background: [background if provided]
|
||||
```
|
||||
|
||||
## 📝 Feedback to Provide
|
||||
|
||||
- UI/UX impressions
|
||||
- Any bugs or errors
|
||||
- Performance issues
|
||||
- Suggested improvements
|
||||
- Missing features
|
||||
|
||||
---
|
||||
|
||||
**Ready to test!** Start both servers and follow the steps above.
|
||||
@@ -1,7 +1,7 @@
|
||||
# 🎯 MVP Progress Report
|
||||
|
||||
**Last Updated:** October 11, 2025
|
||||
**Status:** Phase 1 Complete, Moving to Phase 2
|
||||
**Last Updated:** October 12, 2025
|
||||
**Status:** Phase 2 Complete, Moving to Phase 3
|
||||
|
||||
---
|
||||
|
||||
@@ -70,32 +70,48 @@
|
||||
- Public/private message flow ✅
|
||||
- WebSocket handling for all types ✅
|
||||
|
||||
### 🔄 Phase 2: Character Profile System (NEXT)
|
||||
**Target:** Week 3-4
|
||||
### ✅ Phase 2: Character Profile System (COMPLETE)
|
||||
**Completed:** October 12, 2025
|
||||
|
||||
**Tasks:**
|
||||
1. Extend `Character` model with profile fields
|
||||
**Implemented:**
|
||||
1. ✅ Extended `Character` model with profile fields
|
||||
- Gender (Male/Female/Non-binary/Custom)
|
||||
- Race (Human/Elf/Dwarf/Orc/Halfling)
|
||||
- Class (Warrior/Wizard/Cleric/Archer/Rogue)
|
||||
- Personality (Friendly/Serious/Doubtful/Measured)
|
||||
- Custom background text
|
||||
- Avatar upload/selection
|
||||
- Avatar data field (base64)
|
||||
|
||||
2. Profile-based LLM prompts
|
||||
- Combine race + class + personality traits
|
||||
- Inject into character's LLM requests
|
||||
- Create prompt template system
|
||||
2. ✅ Profile-based LLM prompts
|
||||
- Combined race + class + personality traits
|
||||
- Injected into character's LLM requests
|
||||
- Created comprehensive prompt template system
|
||||
- `build_character_system_prompt()` function
|
||||
|
||||
3. Character creation wizard
|
||||
- Multi-step form with dropdowns
|
||||
- Profile preview
|
||||
- Character customization
|
||||
3. ✅ Character creation wizard
|
||||
- 6-step form with visual selection cards
|
||||
- Profile preview and review step
|
||||
- Character customization with all options
|
||||
- Import from JSON functionality
|
||||
|
||||
4. Import/Export system
|
||||
- Export to JSON
|
||||
- Export to PNG with metadata
|
||||
- Import from JSON/PNG
|
||||
4. ✅ Import/Export system
|
||||
- Export to JSON (complete)
|
||||
- Import from JSON (complete)
|
||||
- Export button in CharacterView
|
||||
- PNG with metadata (deferred to Phase 4)
|
||||
|
||||
**New Files:**
|
||||
- `CharacterCreationWizard.js` (419 lines)
|
||||
- `CharacterCreationWizard.css` (352 lines)
|
||||
- `PHASE2_IMPLEMENTATION.md` (documentation)
|
||||
|
||||
**Modified Files:**
|
||||
- `main.py` (+186 lines)
|
||||
- `SessionSetup.js` (+25 lines)
|
||||
- `CharacterView.js` (+30 lines)
|
||||
- `App.css` (+45 lines)
|
||||
|
||||
**Total:** ~1,057 lines of code
|
||||
|
||||
### ⏳ Phase 3: User Mode Interfaces (Weeks 5-7)
|
||||
- Player interface refinement
|
||||
|
||||
351
docs/development/PHASE2_IMPLEMENTATION.md
Normal file
351
docs/development/PHASE2_IMPLEMENTATION.md
Normal file
@@ -0,0 +1,351 @@
|
||||
# Phase 2 Implementation Summary
|
||||
|
||||
**Date:** October 12, 2025
|
||||
**Status:** ✅ Complete
|
||||
**Phase:** Character Profile System (MVP Phase 2)
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Overview
|
||||
|
||||
Successfully implemented the Character Profile System as outlined in the MVP Roadmap. This phase adds structured character creation with race, class, gender, and personality traits, along with profile-based LLM prompts and import/export functionality.
|
||||
|
||||
---
|
||||
|
||||
## ✅ Completed Features
|
||||
|
||||
### 1. Backend: Character Profile Model
|
||||
|
||||
**File:** `main.py`
|
||||
|
||||
Added `CharacterProfile` model with:
|
||||
- **Gender:** Male, Female, Non-binary, Custom
|
||||
- **Race:** Human, Elf, Dwarf, Orc, Halfling
|
||||
- **Class:** Warrior, Wizard, Cleric, Archer, Rogue
|
||||
- **Personality Type:** Friendly, Serious, Doubtful, Measured
|
||||
- **Background:** Custom background story
|
||||
- **Avatar Data:** Base64 encoded avatar (placeholder for future image support)
|
||||
|
||||
Extended `Character` model to include optional `profile` field for backward compatibility with legacy characters.
|
||||
|
||||
### 2. Backend: Prompt Template System
|
||||
|
||||
**File:** `main.py` (lines 76-129)
|
||||
|
||||
Created comprehensive prompt templates:
|
||||
|
||||
#### Race Templates
|
||||
- **Human:** Versatile and adaptable
|
||||
- **Elf:** Graceful, wise, with keen senses and magic affinity
|
||||
- **Dwarf:** Stout, loyal, master craftsmen
|
||||
- **Orc:** Powerful, direct, honorable warriors
|
||||
- **Halfling:** Small, brave, lucky
|
||||
|
||||
#### Class Templates
|
||||
- **Warrior:** Physical combat, tactics, protection
|
||||
- **Wizard:** Arcane magic, knowledge, intellectual approach
|
||||
- **Cleric:** Divine power, healing, compassion
|
||||
- **Archer:** Ranged combat, precision, patience
|
||||
- **Rogue:** Stealth, cunning, unconventional solutions
|
||||
|
||||
#### Personality Templates
|
||||
- **Friendly:** Optimistic, cooperative, trusting
|
||||
- **Serious:** Focused, pragmatic, efficient
|
||||
- **Doubtful:** Cautious, skeptical, analytical
|
||||
- **Measured:** Balanced, thoughtful, diplomatic
|
||||
|
||||
**Function:** `build_character_system_prompt(character: Character) -> str`
|
||||
- Combines all profile traits into cohesive system prompt
|
||||
- Maintains backward compatibility with legacy characters
|
||||
- Injects profile context into LLM requests
|
||||
|
||||
### 3. Backend: API Endpoints
|
||||
|
||||
**New Endpoints:**
|
||||
|
||||
#### Character Creation (Updated)
|
||||
```
|
||||
POST /sessions/{session_id}/characters/
|
||||
Body: CreateCharacterRequest (JSON with optional profile)
|
||||
```
|
||||
|
||||
#### Legacy Character Creation (Backward Compatible)
|
||||
```
|
||||
POST /sessions/{session_id}/characters/legacy/
|
||||
Query params: name, description, personality, llm_model
|
||||
```
|
||||
|
||||
#### Export Character
|
||||
```
|
||||
GET /sessions/{session_id}/characters/{character_id}/export
|
||||
Returns: JSON with character data, version, timestamp
|
||||
```
|
||||
|
||||
#### Import Character
|
||||
```
|
||||
POST /sessions/{session_id}/characters/import
|
||||
Body: { character_data: {...} }
|
||||
```
|
||||
|
||||
#### Profile Options
|
||||
```
|
||||
GET /profile/options
|
||||
Returns: Available genders, races, classes, personalities with descriptions
|
||||
```
|
||||
|
||||
### 4. Frontend: Character Creation Wizard
|
||||
|
||||
**File:** `frontend/src/components/CharacterCreationWizard.js`
|
||||
|
||||
6-step wizard interface:
|
||||
1. **Basic Info:** Name, gender, import option
|
||||
2. **Description:** Character description and background
|
||||
3. **Race & Class:** Visual selection cards with descriptions
|
||||
4. **Personality:** Personality type selection
|
||||
5. **AI Model:** LLM model selection with descriptions
|
||||
6. **Review:** Complete character preview before creation
|
||||
|
||||
**Features:**
|
||||
- Progressive disclosure design
|
||||
- Visual progress indicator
|
||||
- Selection cards with hover effects
|
||||
- Import from JSON
|
||||
- Form validation
|
||||
- Responsive design
|
||||
|
||||
**File:** `frontend/src/components/CharacterCreationWizard.css`
|
||||
- Modern dark theme matching application style
|
||||
- Smooth animations and transitions
|
||||
- Mobile-responsive grid layouts
|
||||
- Visual feedback on selections
|
||||
|
||||
### 5. Frontend: SessionSetup Integration
|
||||
|
||||
**File:** `frontend/src/components/SessionSetup.js`
|
||||
|
||||
Updated to support both wizard and simple character creation:
|
||||
- **Wizard Mode:** Full character creation with profile
|
||||
- **Quick Create:** Toggle for simple legacy mode
|
||||
- Import character JSON during wizard
|
||||
- Session ID validation before opening wizard
|
||||
|
||||
### 6. Frontend: Character Export
|
||||
|
||||
**File:** `frontend/src/components/CharacterView.js`
|
||||
|
||||
Added export functionality:
|
||||
- Export button in character header
|
||||
- Downloads JSON file with character data
|
||||
- Filename includes character name and date
|
||||
- Profile badges display in character info
|
||||
|
||||
### 7. CSS Updates
|
||||
|
||||
**File:** `frontend/src/App.css`
|
||||
|
||||
Added styles for:
|
||||
- Character profile badges
|
||||
- Character actions container
|
||||
- Export button styling
|
||||
- Character creation options
|
||||
- Wizard button styling
|
||||
- Mobile responsive adjustments
|
||||
|
||||
---
|
||||
|
||||
## 🔧 Technical Implementation Details
|
||||
|
||||
### Profile-Based LLM Prompts
|
||||
|
||||
The system now generates context-aware prompts by combining:
|
||||
1. Character name and basic identity
|
||||
2. Race traits (from RACE_PROMPTS)
|
||||
3. Class abilities (from CLASS_PROMPTS)
|
||||
4. Personality traits (from PERSONALITY_PROMPTS)
|
||||
5. Custom background (if provided)
|
||||
6. Legacy personality field (backward compatible)
|
||||
|
||||
**Example Generated Prompt:**
|
||||
```
|
||||
You are Thorin, a male Dwarf Warrior. A grizzled veteran seeking redemption.
|
||||
You are a dwarf, stout and honorable with deep knowledge of stone and metal.
|
||||
You are loyal, practical, and value tradition. You excel in physical combat
|
||||
and tactics, preferring direct action and protecting your allies. You are
|
||||
brave and decisive in battle. You are serious and focused, prioritizing
|
||||
efficiency and practical solutions. You are disciplined and value getting
|
||||
things done. Background: Former guardian of the Mountain Keep, exiled after
|
||||
a tragic failure.
|
||||
```
|
||||
|
||||
### Import/Export Format
|
||||
|
||||
**Export Structure:**
|
||||
```json
|
||||
{
|
||||
"version": "1.0",
|
||||
"character": {
|
||||
"id": "...",
|
||||
"name": "Character Name",
|
||||
"description": "...",
|
||||
"profile": {
|
||||
"gender": "Male",
|
||||
"race": "Elf",
|
||||
"character_class": "Wizard",
|
||||
"personality_type": "Measured",
|
||||
"background": "...",
|
||||
"avatar_data": null
|
||||
},
|
||||
"llm_model": "gpt-4o",
|
||||
"conversation_history": [],
|
||||
"pending_response": false
|
||||
},
|
||||
"created_at": "2025-10-12T00:00:00",
|
||||
"export_type": "storyteller_rpg_character"
|
||||
}
|
||||
```
|
||||
|
||||
**Import Process:**
|
||||
1. Validates JSON structure
|
||||
2. Extracts character data
|
||||
3. Generates new ID to avoid conflicts
|
||||
4. Clears conversation history
|
||||
5. Adds to session
|
||||
6. Notifies storyteller via WebSocket
|
||||
|
||||
### Backward Compatibility
|
||||
|
||||
The system maintains full backward compatibility:
|
||||
- Legacy characters without profiles still work
|
||||
- `build_character_system_prompt()` handles both types
|
||||
- Legacy endpoint available at `/characters/legacy/`
|
||||
- Simple creation mode in SessionSetup
|
||||
|
||||
---
|
||||
|
||||
## 📊 Files Changed
|
||||
|
||||
### Backend
|
||||
- `main.py`: +186 lines
|
||||
- CharacterProfile model
|
||||
- Prompt templates
|
||||
- Profile building function
|
||||
- Import/export endpoints
|
||||
- Profile options endpoint
|
||||
- Updated character creation
|
||||
|
||||
### Frontend
|
||||
- `CharacterCreationWizard.js`: +419 lines (new)
|
||||
- `CharacterCreationWizard.css`: +352 lines (new)
|
||||
- `SessionSetup.js`: +25 lines modified
|
||||
- `CharacterView.js`: +30 lines modified
|
||||
- `App.css`: +45 lines modified
|
||||
|
||||
**Total:** ~1,057 lines added/modified
|
||||
|
||||
---
|
||||
|
||||
## 🧪 Testing Checklist
|
||||
|
||||
- [ ] Create character with wizard (all steps)
|
||||
- [ ] Export character to JSON
|
||||
- [ ] Import character from JSON
|
||||
- [ ] Verify profile displays in CharacterView
|
||||
- [ ] Test legacy character creation (simple mode)
|
||||
- [ ] Verify LLM prompts include profile data
|
||||
- [ ] Test backward compatibility with existing characters
|
||||
- [ ] Mobile responsive testing
|
||||
- [ ] Profile options endpoint
|
||||
- [ ] All race/class/personality combinations
|
||||
|
||||
---
|
||||
|
||||
## 🚀 Next Steps (Phase 3)
|
||||
|
||||
According to MVP Roadmap:
|
||||
|
||||
### Phase 3: User Mode Interfaces (Weeks 5-7)
|
||||
1. **Player Interface Refinement**
|
||||
- Enhanced character sheet display
|
||||
- Profile editing
|
||||
- Inventory/stats (if applicable)
|
||||
|
||||
2. **Storyteller Dashboard**
|
||||
- View all character profiles
|
||||
- Profile-aware response generation
|
||||
- AI player profile management
|
||||
|
||||
3. **Gamemaster Control Panel**
|
||||
- Game creation wizard
|
||||
- Player/role assignment
|
||||
- Profile-based AI configuration
|
||||
|
||||
4. **Permission Enforcement**
|
||||
- Backend decorators
|
||||
- Frontend UI restrictions
|
||||
- WebSocket filtering
|
||||
|
||||
---
|
||||
|
||||
## 💡 Known Limitations & Future Improvements
|
||||
|
||||
### Current Limitations
|
||||
1. **Avatar Support:** Profile has `avatar_data` field but no UI for upload
|
||||
2. **PNG Export:** JSON export works, PNG with metadata not yet implemented
|
||||
3. **Profile Editing:** No UI to edit profile after creation
|
||||
4. **Pre-made Templates:** No quick-start character templates
|
||||
|
||||
### Future Enhancements
|
||||
1. **Avatar System:**
|
||||
- Upload images
|
||||
- AI-generated avatars (DALL-E/Stable Diffusion)
|
||||
- Avatar gallery
|
||||
|
||||
2. **PNG Export/Import:**
|
||||
- Embed profile in PNG metadata
|
||||
- Visual character cards
|
||||
|
||||
3. **Profile Templates:**
|
||||
- Pre-made character archetypes
|
||||
- Quick-start templates (Fighter, Mage, Rogue, etc.)
|
||||
- Community-shared templates
|
||||
|
||||
4. **Advanced Profiles:**
|
||||
- Skills and abilities
|
||||
- Equipment/inventory
|
||||
- Stats (HP, MP, etc.)
|
||||
- Character progression/leveling
|
||||
|
||||
5. **Profile Validation:**
|
||||
- Character name uniqueness
|
||||
- Profile completeness checks
|
||||
- Custom validation rules
|
||||
|
||||
---
|
||||
|
||||
## 📝 Documentation Updates Needed
|
||||
|
||||
- [x] Phase 2 implementation summary (this document)
|
||||
- [ ] Update MVP_PROGRESS.md with Phase 2 completion
|
||||
- [ ] Update NEXT_STEPS.md with Phase 3 priorities
|
||||
- [ ] User guide for character creation wizard
|
||||
- [ ] API documentation for new endpoints
|
||||
- [ ] Update CHANGELOG.md
|
||||
|
||||
---
|
||||
|
||||
## 🎉 Achievements
|
||||
|
||||
✅ **Profile System:** Comprehensive character profiles with 5 races, 5 classes, 4 personalities
|
||||
✅ **Smart Prompts:** Context-aware LLM prompts based on character traits
|
||||
✅ **Beautiful UI:** 6-step wizard with modern design
|
||||
✅ **Import/Export:** Full character portability
|
||||
✅ **Backward Compatible:** Legacy characters still work
|
||||
✅ **Extensible:** Easy to add new races, classes, personalities
|
||||
|
||||
**Phase 2 Status:** ✅ COMPLETE
|
||||
|
||||
---
|
||||
|
||||
*Last Updated: October 12, 2025*
|
||||
*Implementation Time: ~3 hours*
|
||||
*Lines of Code: ~1,057*
|
||||
654
docs/reference/UI_DESIGN_PROMPTS.md
Normal file
654
docs/reference/UI_DESIGN_PROMPTS.md
Normal file
@@ -0,0 +1,654 @@
|
||||
# UI Design Prompts - Ready to Use
|
||||
|
||||
**Purpose:** Copy-paste prompts for UI design LLMs (v0.dev, Midjourney, etc.)
|
||||
**Date:** October 12, 2025
|
||||
|
||||
---
|
||||
|
||||
## 🎨 Base Prompt Template
|
||||
|
||||
```
|
||||
Design a modern dark-themed web application interface for a tabletop RPG storytelling platform.
|
||||
|
||||
Visual Style:
|
||||
- Dark theme with purple gradient accents (#667eea to #764ba2)
|
||||
- Card-based layout with rounded corners (8-12px radius)
|
||||
- Smooth shadows for depth and elevation
|
||||
- Clean, modern sans-serif typography
|
||||
- RPG fantasy aesthetic with subtle magical elements
|
||||
|
||||
Color Palette:
|
||||
- Background: Deep dark blue (#1a1a2e, #16213e)
|
||||
- Surface: Dark slate (#2d3748)
|
||||
- Primary: Purple gradient (#667eea to #764ba2)
|
||||
- Text: White/light gray (#ffffff, #e2e8f0)
|
||||
- Accent: Bright purple (#667eea)
|
||||
|
||||
Design Principles:
|
||||
- Clear visual hierarchy
|
||||
- Generous white space
|
||||
- Accessible contrast ratios
|
||||
- Smooth animations and transitions
|
||||
- Mobile-responsive design
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📄 Prompt 1: Session Setup / Landing Page
|
||||
|
||||
```
|
||||
Create a modern dark-themed landing page for an RPG storytelling web app called "Storyteller RPG"
|
||||
|
||||
Page Components:
|
||||
1. Header Section:
|
||||
- Large app title with dice emoji (🎭 Storyteller RPG)
|
||||
- Subtitle: "Private character-storyteller interactions"
|
||||
- Centered layout
|
||||
|
||||
2. Demo Session Card:
|
||||
- Title: "🎲 Demo Session - The Cursed Tavern"
|
||||
- Short description text
|
||||
- Three horizontally arranged buttons:
|
||||
* "🎲 Join as Storyteller" (primary gradient button)
|
||||
* "⚔️ Play as Bargin (Dwarf Warrior)" (character button)
|
||||
* "🏹 Play as Willow (Elf Ranger)" (character button)
|
||||
- Gradient background (gold #ffd89b to teal #19547b)
|
||||
- Rounded corners with padding
|
||||
|
||||
3. Divider:
|
||||
- Horizontal line with centered text "OR CREATE YOUR OWN"
|
||||
|
||||
4. Create Session Section:
|
||||
- White card with shadow
|
||||
- Title: "Create New Session"
|
||||
- Description: "Start a new game as the storyteller"
|
||||
- Text input field for session name
|
||||
- Full-width primary button: "Create Session"
|
||||
|
||||
5. Divider:
|
||||
- Horizontal line with "OR"
|
||||
|
||||
6. Join Session Section:
|
||||
- White card with shadow
|
||||
- Title: "Join Existing Session"
|
||||
- Form with inputs:
|
||||
* Session ID field
|
||||
* Character name field
|
||||
* Character description textarea
|
||||
* Personality textarea (optional)
|
||||
* Model selector dropdown
|
||||
- Large gradient button: "✨ Create Character (Wizard)"
|
||||
- Secondary toggle: "↓ Quick Create"
|
||||
|
||||
Visual Style:
|
||||
- Purple gradient background for page
|
||||
- White content cards with soft shadows
|
||||
- Centered layout, max-width 600px
|
||||
- Generous padding and spacing
|
||||
- Modern, clean, inviting design
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📄 Prompt 2: Character View (Player Interface)
|
||||
|
||||
```
|
||||
Design a dark-themed character view interface for a player in an RPG session
|
||||
|
||||
Layout Structure:
|
||||
- Full-height application with header, scrollable content, and fixed message composer
|
||||
|
||||
Components:
|
||||
|
||||
1. Character Header (Dark gradient #2d3748):
|
||||
- Left side:
|
||||
* Character name (large, white)
|
||||
* Character description (gray text)
|
||||
* Personality trait with emoji (🎭)
|
||||
* Three profile badges: Race | Class | Personality
|
||||
(Pills with purple accent color)
|
||||
- Right side:
|
||||
* Export button (📥 Export) with subtle purple background
|
||||
* Connection status indicator:
|
||||
- Green dot "● Connected" when active
|
||||
- Gray dot "○ Disconnected" when offline
|
||||
|
||||
2. Current Scene Card (if active):
|
||||
- Highlighted card with scene icon (📜)
|
||||
- Title: "Current Scene"
|
||||
- Scene description text
|
||||
- Distinct background color from messages
|
||||
|
||||
3. Two-Column Content Area:
|
||||
|
||||
Left Column - Public Messages Feed:
|
||||
- Title: "📢 Public Actions (All Players See)"
|
||||
- Message cards with:
|
||||
* Sender name/icon
|
||||
* Message content
|
||||
* Timestamp
|
||||
* Light background with left purple border accent
|
||||
|
||||
Right Column - Private Conversation:
|
||||
- Title: "💬 Private Conversation with Storyteller"
|
||||
- Chat-style message bubbles:
|
||||
* Character messages: Right-aligned, purple gradient
|
||||
* Storyteller messages: Left-aligned, darker color
|
||||
* Timestamps below each message
|
||||
- Auto-scroll to bottom
|
||||
|
||||
4. Message Composer (Fixed Bottom):
|
||||
- Visibility dropdown selector (Private | Public | Mixed)
|
||||
- For "Mixed" mode:
|
||||
* Two textareas stacked:
|
||||
- "Public action (all players see)..."
|
||||
- "Private action (only storyteller sees)..."
|
||||
* "Send Mixed Message" button
|
||||
- For simple mode:
|
||||
* Single input field (placeholder changes by visibility)
|
||||
* "Send" button
|
||||
- Elevated shadow, dark background
|
||||
|
||||
Visual Style:
|
||||
- Dark theme throughout
|
||||
- Purple accent colors for character messages
|
||||
- Clear visual separation between public and private
|
||||
- Smooth scrolling
|
||||
- Professional messaging interface aesthetic
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📄 Prompt 3: Character Creation Wizard
|
||||
|
||||
```
|
||||
Design a beautiful multi-step character creation wizard modal for an RPG application
|
||||
|
||||
Modal Structure:
|
||||
- Full-screen dark overlay (semi-transparent)
|
||||
- Centered wizard container (max 800px wide)
|
||||
- Dark gradient background (#1a1a2e to #16213e)
|
||||
- Rounded corners with border
|
||||
|
||||
Components:
|
||||
|
||||
1. Wizard Header:
|
||||
- Large title: "Create Your Character"
|
||||
- Progress indicator: 6 step pills arranged horizontally
|
||||
* "1. Basic Info" | "2. Description" | "3. Race & Class" | "4. Personality" | "5. AI Model" | "6. Review"
|
||||
* Active step: Purple gradient background, white text
|
||||
* Inactive steps: Muted gray background, gray text
|
||||
* Completed steps: Dimmed purple
|
||||
- Steps wrap on mobile
|
||||
|
||||
2. Content Area (Changes per step):
|
||||
|
||||
Step 1 - Basic Info:
|
||||
- Text input: "Character Name" (with autofocus glow)
|
||||
- Dropdown: "Gender" (Male, Female, Non-binary, Custom)
|
||||
- Import section:
|
||||
* Light text: "💡 Have an existing character?"
|
||||
* Button: "📥 Import from JSON" (outlined style)
|
||||
|
||||
Step 3 - Race & Class (example):
|
||||
- Grid of 5 selection cards (2-3 columns responsive)
|
||||
- Each card:
|
||||
* Race/Class name (bold white)
|
||||
* Short description (gray)
|
||||
* Unselected: Dark background, light border
|
||||
* Selected: Purple gradient background, bright border, slight shadow
|
||||
* Hover: Lift effect with shadow
|
||||
- Two sections: Race cards, then Class cards
|
||||
|
||||
Step 6 - Review:
|
||||
- Preview card with sections:
|
||||
* Basic Information (list of key-value pairs)
|
||||
* Description (paragraph)
|
||||
* Background (if provided)
|
||||
* AI Model
|
||||
- Summary box at bottom:
|
||||
* Purple gradient background
|
||||
* "Character Summary" heading
|
||||
* Natural language sentence about the character
|
||||
|
||||
3. Wizard Footer:
|
||||
- Left: "Cancel" button (secondary)
|
||||
- Right: Navigation buttons
|
||||
* "← Back" (secondary, only shows steps 2-6)
|
||||
* "Next →" (primary purple gradient, steps 1-5)
|
||||
* "✨ Create Character" (primary gradient, step 6)
|
||||
|
||||
Animations:
|
||||
- Step content fades in with slight upward movement
|
||||
- Card selection: Scale transform + glow
|
||||
- Progress indicator: Smooth transitions
|
||||
- Button hovers: Elevation effect
|
||||
|
||||
Visual Style:
|
||||
- Dark, immersive wizard experience
|
||||
- Purple accent throughout
|
||||
- Clear visual hierarchy
|
||||
- Smooth, modern interactions
|
||||
- Feels guided and professional
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📄 Prompt 4: Storyteller View Dashboard
|
||||
|
||||
```
|
||||
Design a comprehensive storyteller dashboard for managing an RPG game session
|
||||
|
||||
Layout:
|
||||
- Sidebar + main content area (grid layout)
|
||||
- Dark theme with purple accents
|
||||
|
||||
Components:
|
||||
|
||||
1. Header Bar:
|
||||
- Session name (large white text)
|
||||
- Session ID with copy button
|
||||
- "Generate Contextual Response" button (purple gradient)
|
||||
- Connection status indicator
|
||||
|
||||
2. Left Sidebar - Character List:
|
||||
- Title: "Characters in Session"
|
||||
- Scrollable character cards (one per character):
|
||||
* Character name (white)
|
||||
* Small profile badges (Race | Class | Personality)
|
||||
* "Needs Response" red indicator (if pending)
|
||||
* Hover: Light background
|
||||
* Selected: Purple left border + highlighted background
|
||||
- Empty state: "No characters yet" with muted text
|
||||
|
||||
3. Main Content Area - Tabs:
|
||||
|
||||
Tab 1 - Public Actions Feed:
|
||||
- Title: "📢 Recent Public Actions"
|
||||
- Timeline/feed of public messages:
|
||||
* Character avatar/icon
|
||||
* Character name
|
||||
* Action text
|
||||
* Timestamp
|
||||
* Compact card style with left accent
|
||||
|
||||
Tab 2 - Character Conversation (selected character):
|
||||
- Character header showing their profile
|
||||
- Message thread (scrollable):
|
||||
* Character messages (left-aligned)
|
||||
* Storyteller responses (right-aligned, purple)
|
||||
* Timestamps
|
||||
- Response composer section:
|
||||
* Large textarea "Write your response..."
|
||||
* "✨ AI Suggest" button (secondary)
|
||||
* "Send Private Response" button (primary)
|
||||
|
||||
Tab 3 - Scene Narration:
|
||||
- Title: "📜 Broadcast Scene to All Players"
|
||||
- Large textarea for scene description
|
||||
- Context options:
|
||||
* Character selection checkboxes
|
||||
* Additional context input
|
||||
- "Generate with AI" button (secondary)
|
||||
- "Broadcast Scene" button (primary, large)
|
||||
|
||||
4. AI Suggestion Panel (conditional):
|
||||
- Appears when "AI Suggest" clicked
|
||||
- Green accent background
|
||||
- Title: "AI-Generated Suggestion"
|
||||
- Editable textarea with generated response
|
||||
- Model indicator (small text)
|
||||
- Action buttons:
|
||||
* "Use This Response" (success green)
|
||||
* "Regenerate" (secondary)
|
||||
* "Cancel" (text button)
|
||||
|
||||
Visual Style:
|
||||
- Dark command center aesthetic
|
||||
- Clear information hierarchy
|
||||
- Easy to scan character list
|
||||
- Comfortable reading for long text
|
||||
- Purple highlights for storyteller actions
|
||||
- Green highlights for AI features
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📄 Prompt 5: Gamemaster Control Panel
|
||||
|
||||
```
|
||||
Design a powerful gamemaster control panel for managing RPG game sessions
|
||||
|
||||
Layout:
|
||||
- Command center dashboard style
|
||||
- Sidebar navigation + main content panels
|
||||
- Dark theme with multiple accent colors
|
||||
|
||||
Components:
|
||||
|
||||
1. Header:
|
||||
- Title: "Gamemaster Control Panel"
|
||||
- Current game indicator (pill badge)
|
||||
- Quick action buttons:
|
||||
* "Create New Game" (purple gradient)
|
||||
* "Load Game" (secondary)
|
||||
* "Save Game" (secondary)
|
||||
|
||||
2. Left Navigation:
|
||||
- Vertical menu with icons:
|
||||
* Dashboard (overview icon)
|
||||
* Games (list icon)
|
||||
* Players (users icon)
|
||||
* Settings (gear icon)
|
||||
- Active item: Purple left border + highlight
|
||||
|
||||
3. Main Content - Game Creation Wizard:
|
||||
|
||||
Step 2 - Player Slots:
|
||||
- Grid of player slot cards (2-3 columns):
|
||||
* Slot number badge (top-right)
|
||||
* Type toggle: Human | AI (switch component)
|
||||
* If Human:
|
||||
- User selector dropdown
|
||||
- Character assignment
|
||||
* If AI:
|
||||
- AI model dropdown
|
||||
- Personality/behavior settings
|
||||
* Drag handle (for reordering)
|
||||
- "Add Slot" button at end
|
||||
|
||||
Each slot card:
|
||||
- Dark background with border
|
||||
- Assigned: Green accent border
|
||||
- Empty: Dashed border
|
||||
- Hover: Lift effect
|
||||
|
||||
4. Main Content - Game Overview Dashboard:
|
||||
- Metric cards row (4 cards):
|
||||
* Active Players (number + icon)
|
||||
* Total Messages (number + icon)
|
||||
* Session Duration (time + icon)
|
||||
* AI Usage Cost ($ + icon)
|
||||
- Current scene card (large, highlighted)
|
||||
- Recent activity feed
|
||||
- Quick actions panel
|
||||
|
||||
5. Role Assignment Interface:
|
||||
- Drag-and-drop layout:
|
||||
* Left: Available players list (cards)
|
||||
* Right: Game slots (drop zones)
|
||||
* Visual feedback during drag
|
||||
- Each player card:
|
||||
* Avatar/icon
|
||||
* Username
|
||||
* Online status
|
||||
* Drag handle
|
||||
|
||||
Visual Style:
|
||||
- Professional dashboard aesthetic
|
||||
- Multiple status colors (green=good, red=alert, yellow=warning)
|
||||
- Clear data visualization
|
||||
- Interactive drag-and-drop
|
||||
- Elevated cards with shadows
|
||||
- Purple primary, green success, red danger
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📄 Prompt 6: Admin Dashboard
|
||||
|
||||
```
|
||||
Design a comprehensive system administration dashboard for monitoring and management
|
||||
|
||||
Layout:
|
||||
- Full-width dashboard with sidebar navigation
|
||||
- Dark theme with data visualization focus
|
||||
|
||||
Components:
|
||||
|
||||
1. Top Header:
|
||||
- Title: "System Administration"
|
||||
- System status indicators (colored dots):
|
||||
* API Status (green/red)
|
||||
* Database (green/red)
|
||||
* WebSocket (green/red)
|
||||
- Global stats (small numbers):
|
||||
* Active Games: 12
|
||||
* Active Users: 48
|
||||
* API Calls Today: 1,234
|
||||
|
||||
2. Sidebar Navigation:
|
||||
- Vertical menu items:
|
||||
* Dashboard (home icon)
|
||||
* Games (controller icon)
|
||||
* Users (people icon)
|
||||
* LLM Config (brain icon)
|
||||
* Analytics (chart icon)
|
||||
* Costs (dollar icon)
|
||||
* Logs (terminal icon)
|
||||
- Active: Purple background + white icon
|
||||
|
||||
3. Dashboard Overview:
|
||||
- 4 metric cards (top row):
|
||||
* Total Games (number, trend arrow, sparkline)
|
||||
* Total Users (number, trend arrow, sparkline)
|
||||
* Today's Cost ($, trend arrow)
|
||||
* System Health (percentage, circular progress)
|
||||
|
||||
- Charts section:
|
||||
* Line chart: "Games Created Over Time" (7 days)
|
||||
* Bar chart: "Model Usage Distribution"
|
||||
* Pie chart: "Cost Breakdown by Model"
|
||||
|
||||
- Recent Activity Feed:
|
||||
* Timeline of recent events
|
||||
* Color-coded by type (create, error, warning)
|
||||
* Timestamps
|
||||
* Quick action buttons
|
||||
|
||||
4. Games Management Table:
|
||||
- Data table with columns:
|
||||
* ID | Name | GM | Players | Status | Created | Actions
|
||||
- Features:
|
||||
* Sort arrows in headers
|
||||
* Search bar (top-right)
|
||||
* Filter chips (by status)
|
||||
* Pagination controls (bottom)
|
||||
- Row actions:
|
||||
* View (eye icon)
|
||||
* Edit (pencil icon)
|
||||
* Delete (trash icon)
|
||||
- Status badges (colored):
|
||||
* Active (green)
|
||||
* Paused (yellow)
|
||||
* Completed (gray)
|
||||
|
||||
5. Cost Analytics View:
|
||||
- Summary cards (top):
|
||||
* This Month ($)
|
||||
* Per Game Average ($)
|
||||
* Most Expensive Model (name + $)
|
||||
- Cost breakdown table:
|
||||
* Model | Calls | Total Cost | Avg Per Call
|
||||
* Sortable columns
|
||||
- Date range picker (top-right)
|
||||
- Export CSV button
|
||||
|
||||
Visual Style:
|
||||
- Professional admin interface
|
||||
- Data-focused with clear metrics
|
||||
- Color-coded status indicators
|
||||
- Clean tables with good readability
|
||||
- Charts with tooltips
|
||||
- Responsive grid layouts
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Specialized Component Prompts
|
||||
|
||||
### Prompt: Message Bubble Component
|
||||
|
||||
```
|
||||
Design a modern chat message bubble component for a dark-themed RPG interface
|
||||
|
||||
Requirements:
|
||||
- Two variants: Character (sent) and Storyteller (received)
|
||||
- Character messages:
|
||||
* Right-aligned
|
||||
* Purple gradient background (#667eea to #764ba2)
|
||||
* White text
|
||||
* Rounded corners (more rounded on left side)
|
||||
* Small shadow
|
||||
- Storyteller messages:
|
||||
* Left-aligned
|
||||
* Dark gray background (#374151)
|
||||
* Light gray text
|
||||
* Rounded corners (more rounded on right side)
|
||||
* Subtle border
|
||||
- Both include:
|
||||
* Message content (wrapped text)
|
||||
* Timestamp (small, muted, below bubble)
|
||||
* Sender name (optional, above bubble)
|
||||
- Smooth entry animation (fade + slide)
|
||||
- Hover: Slight shadow increase
|
||||
```
|
||||
|
||||
### Prompt: Selection Card Component
|
||||
|
||||
```
|
||||
Design an interactive selection card for character race/class/personality selection
|
||||
|
||||
States:
|
||||
1. Default:
|
||||
- Dark background (#2d3748)
|
||||
- Light border (rgba(255,255,255,0.1))
|
||||
- Rounded corners (10px)
|
||||
- Padding: 20px
|
||||
- Content:
|
||||
* Title (bold, white, 16px)
|
||||
* Description (gray, 13px)
|
||||
|
||||
2. Hover:
|
||||
- Background: Slightly lighter
|
||||
- Border: Purple tint
|
||||
- Transform: translateY(-2px)
|
||||
- Shadow: Elevated
|
||||
|
||||
3. Selected:
|
||||
- Background: Purple gradient (subtle)
|
||||
- Border: Bright purple (#667eea)
|
||||
- Shadow: Purple glow
|
||||
- Checkmark icon (top-right corner)
|
||||
|
||||
Animation:
|
||||
- Smooth transition on all state changes
|
||||
- Scale slightly on click
|
||||
- Ripple effect on selection
|
||||
|
||||
Size:
|
||||
- Min width: 200px
|
||||
- Flexible height based on content
|
||||
- Grid-friendly
|
||||
```
|
||||
|
||||
### Prompt: Progress Indicator Component
|
||||
|
||||
```
|
||||
Design a multi-step progress indicator for a wizard interface
|
||||
|
||||
Components:
|
||||
- 6 steps arranged horizontally
|
||||
- Each step:
|
||||
* Number or icon
|
||||
* Label text below
|
||||
* Connecting line to next step
|
||||
|
||||
States per step:
|
||||
1. Completed:
|
||||
- Checkmark icon (white)
|
||||
- Purple filled circle
|
||||
- Purple line to next
|
||||
- Label: Purple, smaller
|
||||
|
||||
2. Active/Current:
|
||||
- Number in white
|
||||
- Purple gradient circle (larger)
|
||||
- Pulsing glow animation
|
||||
- Label: White, bold
|
||||
|
||||
3. Upcoming:
|
||||
- Number in gray
|
||||
- Gray outlined circle
|
||||
- Gray dashed line to next
|
||||
- Label: Gray, normal
|
||||
|
||||
Responsive:
|
||||
- Desktop: Horizontal line
|
||||
- Mobile: Vertical or wrapped
|
||||
|
||||
Visual Style:
|
||||
- Modern, clean
|
||||
- Clear current position
|
||||
- Motivating progress visualization
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📱 Mobile-Specific Prompts
|
||||
|
||||
### Prompt: Mobile Navigation
|
||||
|
||||
```
|
||||
Design a mobile-friendly bottom navigation bar for the RPG app
|
||||
|
||||
Requirements:
|
||||
- Fixed to bottom of screen
|
||||
- Dark background with slight transparency
|
||||
- 4-5 navigation items:
|
||||
* Home/Session (house icon)
|
||||
* Character (person icon)
|
||||
* Messages (chat icon)
|
||||
* More (dots icon)
|
||||
- Active item:
|
||||
* Purple icon color
|
||||
* Label text (white)
|
||||
* Indicator line on top
|
||||
- Inactive items:
|
||||
* Gray icon
|
||||
* Small label (optional)
|
||||
- Badge notifications (red dot on icons)
|
||||
- Safe area insets for iOS
|
||||
- Subtle shadow on top edge
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🎨 Using These Prompts
|
||||
|
||||
### With v0.dev (Vercel):
|
||||
```
|
||||
Copy base template + specific page prompt
|
||||
Add: "Generate React/Next.js components with Tailwind CSS"
|
||||
Review generated code and iterate
|
||||
```
|
||||
|
||||
### With Midjourney/DALL-E:
|
||||
```
|
||||
Copy prompt
|
||||
Add: "UI mockup, high fidelity, Figma style"
|
||||
Generate multiple variations
|
||||
Use as design reference
|
||||
```
|
||||
|
||||
### With Claude/GPT:
|
||||
```
|
||||
Copy prompt
|
||||
Add: "Generate HTML/CSS code for this design"
|
||||
or "Create a React component for this"
|
||||
Iterate on the implementation
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
**All prompts are ready to copy and use!** Customize colors, spacing, or specific elements as needed.
|
||||
890
docs/reference/UI_ELEMENTS_INVENTORY.md
Normal file
890
docs/reference/UI_ELEMENTS_INVENTORY.md
Normal file
@@ -0,0 +1,890 @@
|
||||
# UI Elements Inventory - Storyteller RPG
|
||||
|
||||
**Purpose:** Comprehensive list of UI elements organized by page for design template generation
|
||||
**Date:** October 12, 2025
|
||||
**Status:** Phase 2 Complete, Planning Phase 3
|
||||
|
||||
---
|
||||
|
||||
## 🎨 Design System Overview
|
||||
|
||||
### Color Palette
|
||||
- **Primary Gradient:** #667eea to #764ba2 (purple gradient)
|
||||
- **Secondary Gradient:** #ffd89b to #19547b (gold to teal)
|
||||
- **Background Dark:** #1a1a2e, #16213e
|
||||
- **Surface Dark:** #2d3748
|
||||
- **Text Light:** #ffffff, #e2e8f0
|
||||
- **Text Muted:** #a0aec0, #718096
|
||||
- **Accent:** #667eea (purple)
|
||||
- **Success:** #10b981, #34d399
|
||||
- **Warning:** #f59e0b
|
||||
- **Error:** #ef4444
|
||||
|
||||
### Typography
|
||||
- **Font Family:** -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', sans-serif
|
||||
- **H1:** 2.5rem, bold
|
||||
- **H2:** 2rem, bold
|
||||
- **H3:** 1.5rem, semibold
|
||||
- **Body:** 1rem
|
||||
- **Small:** 0.875rem
|
||||
|
||||
### Spacing Scale
|
||||
- **xs:** 0.25rem (4px)
|
||||
- **sm:** 0.5rem (8px)
|
||||
- **md:** 1rem (16px)
|
||||
- **lg:** 1.5rem (24px)
|
||||
- **xl:** 2rem (32px)
|
||||
- **2xl:** 3rem (48px)
|
||||
|
||||
### Border Radius
|
||||
- **Small:** 6px
|
||||
- **Medium:** 8px
|
||||
- **Large:** 12px
|
||||
- **XLarge:** 20px
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 1: Session Setup / Landing Page
|
||||
|
||||
### Purpose
|
||||
Entry point for creating or joining game sessions
|
||||
|
||||
### Layout Structure
|
||||
```
|
||||
┌─────────────────────────────────────┐
|
||||
│ Header (Logo + Title) │
|
||||
├─────────────────────────────────────┤
|
||||
│ │
|
||||
│ Demo Session Cards │
|
||||
│ │
|
||||
├─────────────────────────────────────┤
|
||||
│ │
|
||||
│ Create New Session Section │
|
||||
│ │
|
||||
├─────────────────────────────────────┤
|
||||
│ │
|
||||
│ Join Existing Session Section │
|
||||
│ │
|
||||
└─────────────────────────────────────┘
|
||||
```
|
||||
|
||||
### UI Elements
|
||||
|
||||
#### **Header Section**
|
||||
- **App Title:** Large heading with emoji (🎭 Storyteller RPG)
|
||||
- **Subtitle:** Descriptive tagline
|
||||
- **Logo/Icon:** Optional app icon
|
||||
|
||||
#### **Demo Section**
|
||||
- **Section Title:** "🎲 Demo Session - The Cursed Tavern"
|
||||
- **Description Text:** Short description paragraph
|
||||
- **Button Group (3 buttons):**
|
||||
- Storyteller button (🎲 icon, primary style)
|
||||
- Character 1 button (⚔️ icon, character style)
|
||||
- Character 2 button (🏹 icon, character style)
|
||||
- **Visual Style:** Gradient background, rounded corners
|
||||
|
||||
#### **Divider Elements**
|
||||
- **Text Divider:** "OR CREATE YOUR OWN" / "OR"
|
||||
- **Horizontal line with text overlay**
|
||||
|
||||
#### **Create Session Section**
|
||||
- **Section Title:** "Create New Session"
|
||||
- **Section Description:** "Start a new game as the storyteller"
|
||||
- **Input Field:** Text input for session name
|
||||
- **Primary Button:** "Create Session" (full width)
|
||||
- **Visual Style:** White card with shadow
|
||||
|
||||
#### **Join Session Section**
|
||||
- **Section Title:** "Join Existing Session"
|
||||
- **Section Description:** "Play as a character in an ongoing game"
|
||||
- **Form Elements:**
|
||||
- Session ID input field
|
||||
- Character name input field
|
||||
- Character description textarea
|
||||
- Personality traits textarea (optional)
|
||||
- Model selector dropdown (grouped options)
|
||||
- Model hint text
|
||||
- **Action Buttons:**
|
||||
- "✨ Create Character (Wizard)" - Primary gradient button
|
||||
- "↓ Quick Create" toggle - Secondary button
|
||||
- "Join Session (Simple)" - Conditional primary button
|
||||
- **Visual Style:** White card with shadow
|
||||
|
||||
### Responsive Behavior
|
||||
- **Desktop:** Single column, max-width 600px, centered
|
||||
- **Mobile:** Full width, stacked elements
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 2: Character View (Player Interface)
|
||||
|
||||
### Purpose
|
||||
Interface for players to interact with storyteller and view game state
|
||||
|
||||
### Layout Structure
|
||||
```
|
||||
┌─────────────────────────────────────────────────┐
|
||||
│ Character Header (Info + Status) │
|
||||
├─────────────────────────────────────────────────┤
|
||||
│ Current Scene Card (if active) │
|
||||
├─────────────────────────────────────────────────┤
|
||||
│ │
|
||||
│ ┌─────────────────┬─────────────────────────┐ │
|
||||
│ │ Public Messages │ Private Conversation │ │
|
||||
│ │ Feed │ with Storyteller │ │
|
||||
│ │ │ │ │
|
||||
│ │ │ │ │
|
||||
│ └─────────────────┴─────────────────────────┘ │
|
||||
│ │
|
||||
├─────────────────────────────────────────────────┤
|
||||
│ Message Composer (Bottom) │
|
||||
└─────────────────────────────────────────────────┘
|
||||
```
|
||||
|
||||
### UI Elements
|
||||
|
||||
#### **Character Header**
|
||||
- **Character Name:** Large heading
|
||||
- **Character Description:** Paragraph text
|
||||
- **Personality Trait:** Small text with emoji (🎭)
|
||||
- **Profile Badges:** 3 pill-shaped badges
|
||||
- Race badge
|
||||
- Class badge
|
||||
- Personality type badge
|
||||
- **Action Buttons:**
|
||||
- Export button (📥 Export)
|
||||
- **Status Indicator:** Connection status dot
|
||||
- Connected: Green dot + "● Connected"
|
||||
- Disconnected: Gray dot + "○ Disconnected"
|
||||
- **Visual Style:** Dark gradient background, rounded top corners
|
||||
|
||||
#### **Current Scene Card** (Conditional)
|
||||
- **Section Title:** "📜 Current Scene"
|
||||
- **Scene Text:** Paragraph with scene description
|
||||
- **Visual Style:** Highlighted card, distinct from messages
|
||||
|
||||
#### **Public Messages Section**
|
||||
- **Section Title:** "📢 Public Actions (All Players See)"
|
||||
- **Message List:**
|
||||
- Message bubble/card per public action
|
||||
- Sender indicator (🎭 Public Action / 🎲 Scene)
|
||||
- Message content
|
||||
- Timestamp (small, muted)
|
||||
- **Visual Style:** Light background, left border accent
|
||||
|
||||
#### **Private Conversation Section**
|
||||
- **Section Title:** "💬 Private Conversation with Storyteller"
|
||||
- **Message List:**
|
||||
- Message bubbles alternating left/right
|
||||
- Character messages (right aligned, purple)
|
||||
- Storyteller messages (left aligned, different color)
|
||||
- Timestamps
|
||||
- **Scroll Behavior:** Auto-scroll to bottom on new message
|
||||
|
||||
#### **Message Composer** (Bottom Section)
|
||||
- **Visibility Selector:** Dropdown
|
||||
- Options: Private, Public, Mixed
|
||||
- **Mixed Mode Form:**
|
||||
- Public textarea: "Public action (all players see)..."
|
||||
- Private textarea: "Private action (only storyteller sees)..."
|
||||
- Send button: "Send Mixed Message"
|
||||
- **Simple Mode Form:**
|
||||
- Single input field (changes placeholder by visibility)
|
||||
- Send button
|
||||
- **Visual Style:** Fixed to bottom, elevated shadow
|
||||
|
||||
### Component States
|
||||
- **Connected State:** Full functionality enabled
|
||||
- **Disconnected State:** Inputs disabled, gray overlay
|
||||
- **Loading State:** Skeleton screens
|
||||
- **Empty State:** "No messages yet" placeholder
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 3: Character Creation Wizard
|
||||
|
||||
### Purpose
|
||||
Multi-step guided character creation with profile system
|
||||
|
||||
### Layout Structure
|
||||
```
|
||||
┌─────────────────────────────────────────┐
|
||||
│ Wizard Header (Title + Progress) │
|
||||
├─────────────────────────────────────────┤
|
||||
│ │
|
||||
│ │
|
||||
│ Step Content Area │
|
||||
│ (Changes per step) │
|
||||
│ │
|
||||
│ │
|
||||
├─────────────────────────────────────────┤
|
||||
│ Footer (Cancel | Back | Next/Create) │
|
||||
└─────────────────────────────────────────┘
|
||||
```
|
||||
|
||||
### UI Elements
|
||||
|
||||
#### **Wizard Overlay**
|
||||
- **Full-screen modal:** Dark semi-transparent background
|
||||
- **Centered container:** Max 800px width
|
||||
- **Visual Style:** Dark gradient card with border
|
||||
|
||||
#### **Wizard Header**
|
||||
- **Title:** "Create Your Character" (large heading)
|
||||
- **Progress Indicator:** 6 steps
|
||||
- Step pills showing: "1. Basic Info", "2. Description", etc.
|
||||
- Active step highlighted
|
||||
- Completed steps dimmed
|
||||
- Responsive: Wraps on mobile
|
||||
|
||||
#### **Step 1: Basic Info**
|
||||
- **Step Title:** "Basic Information"
|
||||
- **Input Fields:**
|
||||
- Character name (text input, required, autofocus)
|
||||
- Gender dropdown (4 options)
|
||||
- **Import Section:**
|
||||
- Import hint text: "💡 Have an existing character?"
|
||||
- File upload button: "📥 Import from JSON"
|
||||
- Hidden file input (accepts .json)
|
||||
- **Visual Style:** Form inputs with dark theme
|
||||
|
||||
#### **Step 2: Description**
|
||||
- **Step Title:** "Character Description"
|
||||
- **Input Fields:**
|
||||
- Description textarea (required, 4 rows)
|
||||
- Background textarea (optional, 3 rows)
|
||||
- **Visual Style:** Larger text areas, clear labels
|
||||
|
||||
#### **Step 3: Race & Class**
|
||||
- **Step Title:** "Race & Class"
|
||||
- **Race Selection:**
|
||||
- Label: "Race"
|
||||
- Selection grid (responsive, min 200px cards)
|
||||
- 5 clickable cards:
|
||||
- Race name (bold)
|
||||
- Race description (smaller text)
|
||||
- Selected state: gradient background + border
|
||||
- Hover state: slight elevation
|
||||
- **Class Selection:**
|
||||
- Same layout as Race
|
||||
- 5 class cards
|
||||
- **Visual Style:** Grid layout, interactive cards
|
||||
|
||||
#### **Step 4: Personality**
|
||||
- **Step Title:** "Personality Type"
|
||||
- **Selection Grid:**
|
||||
- 4 personality type cards
|
||||
- Same card style as race/class
|
||||
- **Additional Input:**
|
||||
- "Additional Personality Traits" textarea (optional, 3 rows)
|
||||
- **Visual Style:** Consistent with Step 3
|
||||
|
||||
#### **Step 5: AI Model**
|
||||
- **Step Title:** "AI Model Selection"
|
||||
- **Model Dropdown:**
|
||||
- Large dropdown (bigger padding/font)
|
||||
- Grouped options (OpenAI / OpenRouter)
|
||||
- Shows provider in parentheses
|
||||
- **Help Text:**
|
||||
- "💡 Different models give different personalities!"
|
||||
- Multi-line hint text
|
||||
- **Visual Style:** Prominent dropdown, informative hint
|
||||
|
||||
#### **Step 6: Review**
|
||||
- **Step Title:** "Review Your Character"
|
||||
- **Preview Card:**
|
||||
- Multiple sections with borders between:
|
||||
- Basic Information (name, gender, race, class, personality)
|
||||
- Description
|
||||
- Background (if provided)
|
||||
- Additional Traits (if provided)
|
||||
- AI Model
|
||||
- Summary box at bottom:
|
||||
- Highlighted background
|
||||
- "Character Summary" heading
|
||||
- Natural language summary sentence
|
||||
- **Visual Style:** Clean, organized, easy to scan
|
||||
|
||||
#### **Wizard Footer**
|
||||
- **Button Layout:**
|
||||
- Cancel (left, secondary)
|
||||
- Navigation (right):
|
||||
- Back button (steps 2-6, secondary)
|
||||
- Next button (steps 1-5, primary)
|
||||
- Create button (step 6, primary with sparkles)
|
||||
- **Visual Style:** Fixed footer, clear hierarchy
|
||||
|
||||
### Animation & Transitions
|
||||
- **Step Changes:** Fade in with slight upward movement
|
||||
- **Card Selection:** Transform scale + shadow on selection
|
||||
- **Button Hovers:** Slight elevation, color shift
|
||||
- **Progress Indicator:** Smooth transitions between steps
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 4: Storyteller View
|
||||
|
||||
### Purpose
|
||||
Interface for storyteller to manage game, view all character actions, and respond
|
||||
|
||||
### Layout Structure
|
||||
```
|
||||
┌──────────────────────────────────────────────────┐
|
||||
│ Header (Session Info + Controls) │
|
||||
├──────────────────────────────────────────────────┤
|
||||
│ │
|
||||
│ ┌───────────────┬────────────────────────────┐ │
|
||||
│ │ Character │ Main Content Area: │ │
|
||||
│ │ List │ │ │
|
||||
│ │ (Sidebar) │ - Public Actions Feed │ │
|
||||
│ │ │ - Selected Character View │ │
|
||||
│ │ │ - Scene Narration │ │
|
||||
│ │ │ │ │
|
||||
│ └───────────────┴────────────────────────────┘ │
|
||||
│ │
|
||||
└──────────────────────────────────────────────────┘
|
||||
```
|
||||
|
||||
### UI Elements
|
||||
|
||||
#### **Storyteller Header**
|
||||
- **Session Name:** Large heading
|
||||
- **Session ID:** Copy button with ID
|
||||
- **Control Buttons:**
|
||||
- Generate contextual response button
|
||||
- Other session controls
|
||||
- **Visual Style:** Dark header, elevated
|
||||
|
||||
#### **Character List Sidebar**
|
||||
- **Section Title:** "Characters in Session"
|
||||
- **Character Cards:** (One per character)
|
||||
- Character name
|
||||
- Race/Class/Personality badges
|
||||
- "Needs Response" indicator (conditional)
|
||||
- Click to select
|
||||
- Active state highlighting
|
||||
- **Empty State:** "No characters yet" message
|
||||
- **Visual Style:** Scrollable sidebar, clear selection state
|
||||
|
||||
#### **Public Actions Feed**
|
||||
- **Section Title:** "📢 Recent Public Actions"
|
||||
- **Feed Items:**
|
||||
- Character name/avatar
|
||||
- Public action text
|
||||
- Timestamp
|
||||
- Compact card style
|
||||
- **Visual Style:** Timeline/feed layout
|
||||
|
||||
#### **Character Conversation View**
|
||||
- **Character Header:**
|
||||
- Selected character name
|
||||
- Profile info
|
||||
- **Conversation Thread:**
|
||||
- Message list (character + storyteller messages)
|
||||
- Clear visual distinction between senders
|
||||
- Timestamps
|
||||
- **Response Composer:**
|
||||
- Textarea for response
|
||||
- "✨ AI Suggest" button
|
||||
- "Send Private Response" button
|
||||
- **Visual Style:** Similar to character view but reversed perspective
|
||||
|
||||
#### **AI Suggestion Modal/Section**
|
||||
- **Generated Response Display:**
|
||||
- Title: "AI-Generated Suggestion"
|
||||
- Response content (editable)
|
||||
- Model used indicator
|
||||
- **Action Buttons:**
|
||||
- "Use This Response"
|
||||
- "Regenerate"
|
||||
- "Cancel"
|
||||
- **Visual Style:** Highlighted section, easy to edit
|
||||
|
||||
#### **Scene Narration Section**
|
||||
- **Section Title:** "Broadcast Scene to All Players"
|
||||
- **Input Field:**
|
||||
- Large textarea for scene description
|
||||
- Character count/hint
|
||||
- **Contextual Generation:**
|
||||
- "Generate with AI" button
|
||||
- Character selection checkboxes
|
||||
- Additional context input
|
||||
- **Send Button:** "📜 Broadcast Scene"
|
||||
- **Visual Style:** Prominent, distinct from private responses
|
||||
|
||||
### Responsive Behavior
|
||||
- **Desktop:** Sidebar + main content (grid layout)
|
||||
- **Tablet:** Collapsible sidebar
|
||||
- **Mobile:** Stack vertically, tab navigation
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 5: Gamemaster Control Panel (Phase 3)
|
||||
|
||||
### Purpose
|
||||
Admin interface to create games, assign roles, and manage session
|
||||
|
||||
### Layout Structure
|
||||
```
|
||||
┌────────────────────────────────────────────┐
|
||||
│ GM Header (Game Info + Quick Actions) │
|
||||
├────────────────────────────────────────────┤
|
||||
│ │
|
||||
│ ┌──────────────┬──────────────────────┐ │
|
||||
│ │ Game │ Main Panel: │ │
|
||||
│ │ Sessions │ │ │
|
||||
│ │ List │ - Game Setup Wizard │ │
|
||||
│ │ │ - Role Assignment │ │
|
||||
│ │ │ - Player Management │ │
|
||||
│ │ │ - Game State View │ │
|
||||
│ │ │ │ │
|
||||
│ └──────────────┴──────────────────────┘ │
|
||||
│ │
|
||||
└────────────────────────────────────────────┘
|
||||
```
|
||||
|
||||
### UI Elements
|
||||
|
||||
#### **GM Dashboard Header**
|
||||
- **Title:** "Gamemaster Control Panel"
|
||||
- **Active Game Indicator:** Current game name
|
||||
- **Quick Actions:**
|
||||
- "Create New Game" button
|
||||
- "Load Game" button
|
||||
- "Save Game" button
|
||||
- **Visual Style:** Command center aesthetic
|
||||
|
||||
#### **Game Sessions List**
|
||||
- **List Items:** (Per game)
|
||||
- Game name
|
||||
- Status badge (not started, active, paused, completed)
|
||||
- Player count
|
||||
- Created date
|
||||
- Actions: View, Edit, Delete
|
||||
- **Visual Style:** Card list, status colors
|
||||
|
||||
#### **Game Creation Wizard**
|
||||
- **Step 1: Game Info**
|
||||
- Game name input
|
||||
- Scenario/setting textarea
|
||||
- Genre/theme selector
|
||||
- **Step 2: Player Slots**
|
||||
- Slot configuration (number input)
|
||||
- Slot cards:
|
||||
- Slot type (Human/AI toggle)
|
||||
- Player assignment (if human)
|
||||
- AI configuration (if AI)
|
||||
- **Step 3: Storyteller Assignment**
|
||||
- Radio buttons: Human / AI
|
||||
- User selector (if human)
|
||||
- AI model selector (if AI)
|
||||
- Storytelling style dropdown
|
||||
- **Step 4: Game Settings**
|
||||
- Turn-based toggle
|
||||
- Auto-save interval
|
||||
- Other game rules
|
||||
- **Visual Style:** Multi-step wizard like character creation
|
||||
|
||||
#### **Role Assignment Interface**
|
||||
- **Player Slots Grid:**
|
||||
- Drag-and-drop cards
|
||||
- Each slot shows:
|
||||
- Slot number
|
||||
- Assigned player/AI
|
||||
- Character info (if selected)
|
||||
- Edit button
|
||||
- **Available Players Panel:**
|
||||
- List of users
|
||||
- Drag to assign
|
||||
- **Visual Style:** Interactive, clear assignment state
|
||||
|
||||
#### **Game State Overview**
|
||||
- **Tabs:**
|
||||
- Overview
|
||||
- Characters
|
||||
- Messages
|
||||
- Timeline
|
||||
- **Overview Tab:**
|
||||
- Game status
|
||||
- Current scene
|
||||
- Active players
|
||||
- Statistics (messages, actions, etc.)
|
||||
- **Characters Tab:**
|
||||
- All character profiles
|
||||
- Stats/inventory (if applicable)
|
||||
- **Messages Tab:**
|
||||
- All messages (public + private)
|
||||
- Filter controls
|
||||
- **Visual Style:** Dashboard with data cards
|
||||
|
||||
#### **AI Storyteller Command Interface**
|
||||
- **Command Input:**
|
||||
- Special input for GM → AI storyteller
|
||||
- Examples: "Introduce a plot twist", "Increase difficulty"
|
||||
- **AI Status:**
|
||||
- Active/paused toggle
|
||||
- Last action timestamp
|
||||
- Response queue
|
||||
- **Override Controls:**
|
||||
- Edit AI responses
|
||||
- Take manual control
|
||||
- **Visual Style:** Distinct command interface
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 6: Admin Dashboard (Development/Future)
|
||||
|
||||
### Purpose
|
||||
System-wide administration, monitoring, and configuration
|
||||
|
||||
### Layout Structure
|
||||
```
|
||||
┌────────────────────────────────────────┐
|
||||
│ Admin Header (System Status) │
|
||||
├────────────────────────────────────────┤
|
||||
│ │
|
||||
│ ┌──────────┬──────────────────────┐ │
|
||||
│ │ Nav Menu │ Content Panel │ │
|
||||
│ │ │ │ │
|
||||
│ │ - Games │ (Changes per menu) │ │
|
||||
│ │ - Users │ │ │
|
||||
│ │ - Models │ │ │
|
||||
│ │ - Costs │ │ │
|
||||
│ │ - Logs │ │ │
|
||||
│ │ │ │ │
|
||||
│ └──────────┴──────────────────────┘ │
|
||||
│ │
|
||||
└────────────────────────────────────────┘
|
||||
```
|
||||
|
||||
### UI Elements
|
||||
|
||||
#### **Admin Header**
|
||||
- **Title:** "System Administration"
|
||||
- **System Status Indicators:**
|
||||
- API status (green/red dot)
|
||||
- Active games count
|
||||
- Active users count
|
||||
- **Visual Style:** Dark header, status indicators
|
||||
|
||||
#### **Navigation Menu**
|
||||
- **Menu Items:**
|
||||
- Dashboard (overview)
|
||||
- Games Management
|
||||
- User Management
|
||||
- LLM Configuration
|
||||
- Cost Analytics
|
||||
- System Logs
|
||||
- Settings
|
||||
- **Visual Style:** Vertical menu, active state highlighting
|
||||
|
||||
#### **Dashboard Overview**
|
||||
- **Metric Cards:**
|
||||
- Total games (number + trend)
|
||||
- Total users (number + trend)
|
||||
- API calls today (number + cost)
|
||||
- System health (percentage)
|
||||
- **Recent Activity Feed:**
|
||||
- Latest games created
|
||||
- Recent errors
|
||||
- High-cost requests
|
||||
- **Charts:**
|
||||
- Games over time
|
||||
- Cost over time
|
||||
- Model usage distribution
|
||||
- **Visual Style:** Grid of cards, charts with tooltips
|
||||
|
||||
#### **Games Management**
|
||||
- **Games Table:**
|
||||
- Columns: ID, Name, GM, Players, Status, Created, Actions
|
||||
- Sort controls
|
||||
- Filter controls
|
||||
- Pagination
|
||||
- **Actions:**
|
||||
- View details
|
||||
- Force end
|
||||
- Delete
|
||||
- **Visual Style:** Data table with actions
|
||||
|
||||
#### **User Management**
|
||||
- **Users Table:**
|
||||
- Columns: Username, Email, Role, Games, Joined, Status, Actions
|
||||
- Search bar
|
||||
- Role filter
|
||||
- **Actions:**
|
||||
- Edit role
|
||||
- Suspend/activate
|
||||
- View activity
|
||||
- **Visual Style:** Data table with user cards
|
||||
|
||||
#### **LLM Configuration**
|
||||
- **Model Cards:** (Per model)
|
||||
- Model name
|
||||
- Provider
|
||||
- Status (enabled/disabled toggle)
|
||||
- Usage stats
|
||||
- Cost per token
|
||||
- Edit button
|
||||
- **Add Model Form:**
|
||||
- Model ID input
|
||||
- API key input
|
||||
- Configuration options
|
||||
- **Visual Style:** Grid of model cards
|
||||
|
||||
#### **Cost Analytics**
|
||||
- **Summary Cards:**
|
||||
- Total cost this month
|
||||
- Average per game
|
||||
- Most expensive model
|
||||
- **Cost Breakdown:**
|
||||
- Per model chart
|
||||
- Per game table
|
||||
- Per user table
|
||||
- **Date Range Selector:**
|
||||
- Preset ranges (Today, Week, Month)
|
||||
- Custom range picker
|
||||
- **Export Button:** Download CSV
|
||||
- **Visual Style:** Charts and tables
|
||||
|
||||
#### **System Logs**
|
||||
- **Log Viewer:**
|
||||
- Real-time log stream
|
||||
- Log level filter (Info, Warning, Error)
|
||||
- Search/filter input
|
||||
- Timestamp
|
||||
- Auto-scroll toggle
|
||||
- **Visual Style:** Terminal/console aesthetic
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Common UI Components (Used Across Pages)
|
||||
|
||||
### Buttons
|
||||
- **Primary Button:**
|
||||
- Gradient background (#667eea to #764ba2)
|
||||
- White text, rounded corners
|
||||
- Hover: Slight lift, darker gradient
|
||||
- Sizes: Small, Medium, Large
|
||||
- **Secondary Button:**
|
||||
- Transparent/outlined style
|
||||
- Border color matches theme
|
||||
- Hover: Background color change
|
||||
- **Icon Buttons:**
|
||||
- Circular or square
|
||||
- Icon only, tooltip on hover
|
||||
- **Danger Button:**
|
||||
- Red color scheme
|
||||
- Used for delete/destructive actions
|
||||
|
||||
### Input Fields
|
||||
- **Text Input:**
|
||||
- Dark background with light border
|
||||
- Focus: Border color change, glow effect
|
||||
- Error state: Red border + error message below
|
||||
- Success state: Green border
|
||||
- **Textarea:**
|
||||
- Same as text input but multi-line
|
||||
- Resize handle
|
||||
- **Dropdown/Select:**
|
||||
- Custom styled select
|
||||
- Grouped options support
|
||||
- Search/filter (for long lists)
|
||||
- **Checkbox:**
|
||||
- Custom checkbox with checkmark animation
|
||||
- Label click support
|
||||
- **Radio Buttons:**
|
||||
- Custom styled radio
|
||||
- Clear selected state
|
||||
- **File Upload:**
|
||||
- Drag-and-drop zone
|
||||
- File type indicator
|
||||
- Upload progress
|
||||
|
||||
### Cards
|
||||
- **Base Card:**
|
||||
- Rounded corners (8-12px)
|
||||
- Shadow for elevation
|
||||
- Padding: 1-2rem
|
||||
- Background: White or dark surface
|
||||
- **Interactive Card:**
|
||||
- Hover state: Lift effect
|
||||
- Click state: Scale slightly
|
||||
- Selection state: Border highlight
|
||||
- **Info Card:**
|
||||
- Icon + title + content
|
||||
- Color-coded by type
|
||||
|
||||
### Badges/Pills
|
||||
- **Status Badge:**
|
||||
- Small, rounded pill
|
||||
- Color-coded (green=active, red=error, yellow=warning)
|
||||
- Sizes: XS, SM, MD
|
||||
- **Count Badge:**
|
||||
- Circular badge with number
|
||||
- Often overlays buttons/icons
|
||||
|
||||
### Modals/Overlays
|
||||
- **Modal:**
|
||||
- Full-screen semi-transparent overlay
|
||||
- Centered content container
|
||||
- Close button (X) in top-right
|
||||
- Click outside to close (optional)
|
||||
- **Toast/Notification:**
|
||||
- Slide in from top-right
|
||||
- Auto-dismiss after timeout
|
||||
- Close button
|
||||
- Type: Success, Error, Warning, Info
|
||||
|
||||
### Navigation
|
||||
- **Tabs:**
|
||||
- Horizontal tabs with active state
|
||||
- Underline or background highlight
|
||||
- **Breadcrumbs:**
|
||||
- Path navigation
|
||||
- Separator (/ or >)
|
||||
- Click to navigate
|
||||
- **Pagination:**
|
||||
- Previous/Next buttons
|
||||
- Page numbers
|
||||
- Jump to page input
|
||||
|
||||
### Loading States
|
||||
- **Spinner:**
|
||||
- Circular spinner (small, medium, large)
|
||||
- Themed color
|
||||
- **Skeleton Screen:**
|
||||
- Gray placeholder boxes
|
||||
- Shimmer animation
|
||||
- **Progress Bar:**
|
||||
- Linear progress indicator
|
||||
- Percentage display (optional)
|
||||
|
||||
### Empty States
|
||||
- **No Data:**
|
||||
- Icon + message
|
||||
- Call-to-action button
|
||||
- Helpful hint text
|
||||
- **Error State:**
|
||||
- Error icon + message
|
||||
- Retry button
|
||||
- Support link
|
||||
|
||||
---
|
||||
|
||||
## 📱 Responsive Breakpoints
|
||||
|
||||
### Desktop (1024px+)
|
||||
- Multi-column layouts
|
||||
- Sidebars visible
|
||||
- Full navigation
|
||||
|
||||
### Tablet (768px - 1023px)
|
||||
- Collapsible sidebars
|
||||
- Stacked cards
|
||||
- Simplified navigation
|
||||
|
||||
### Mobile (<768px)
|
||||
- Single column
|
||||
- Bottom navigation
|
||||
- Hamburger menu
|
||||
- Full-screen modals
|
||||
- Larger tap targets
|
||||
|
||||
---
|
||||
|
||||
## ♿ Accessibility Requirements
|
||||
|
||||
### Keyboard Navigation
|
||||
- All interactive elements focusable
|
||||
- Logical tab order
|
||||
- Focus indicators (outline)
|
||||
- Keyboard shortcuts (optional)
|
||||
|
||||
### Screen Reader Support
|
||||
- Semantic HTML
|
||||
- ARIA labels where needed
|
||||
- Alt text for images
|
||||
- Form labels associated
|
||||
|
||||
### Color Contrast
|
||||
- WCAG AA minimum (4.5:1 for text)
|
||||
- Color not sole indicator
|
||||
- High contrast mode support
|
||||
|
||||
### Interaction
|
||||
- Minimum touch target: 44x44px
|
||||
- No timing-critical interactions
|
||||
- Error prevention and recovery
|
||||
|
||||
---
|
||||
|
||||
## 🎨 Animation Guidelines
|
||||
|
||||
### Durations
|
||||
- **Micro:** 100-200ms (hover, focus)
|
||||
- **Short:** 200-300ms (buttons, tooltips)
|
||||
- **Medium:** 300-500ms (modals, page transitions)
|
||||
- **Long:** 500-800ms (complex animations)
|
||||
|
||||
### Easing
|
||||
- **Ease-out:** UI appearing (modal open)
|
||||
- **Ease-in:** UI disappearing (modal close)
|
||||
- **Ease-in-out:** Smooth transitions
|
||||
|
||||
### Motion Preferences
|
||||
- Respect `prefers-reduced-motion`
|
||||
- Disable decorative animations
|
||||
- Keep functional animations
|
||||
|
||||
---
|
||||
|
||||
## 📐 Layout Patterns
|
||||
|
||||
### Container Widths
|
||||
- **Max Width:** 1200px (main content)
|
||||
- **Narrow:** 600px (forms, wizards)
|
||||
- **Wide:** 1400px (dashboards)
|
||||
|
||||
### Grid Systems
|
||||
- **12-column grid** for complex layouts
|
||||
- **Flexbox** for simple layouts
|
||||
- **CSS Grid** for card grids
|
||||
|
||||
### Spacing Rhythm
|
||||
- Consistent vertical rhythm (8px base unit)
|
||||
- Component spacing: 16px, 24px, 32px
|
||||
- Section spacing: 48px, 64px
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Priority Elements for UI Design Templates
|
||||
|
||||
### High Priority (MVP Essential)
|
||||
1. Session Setup page
|
||||
2. Character View
|
||||
3. Character Creation Wizard
|
||||
4. Storyteller View
|
||||
5. Primary buttons and inputs
|
||||
|
||||
### Medium Priority (Phase 3)
|
||||
6. Gamemaster Control Panel
|
||||
7. Role assignment interface
|
||||
8. Game state dashboard
|
||||
|
||||
### Low Priority (Future)
|
||||
9. Admin Dashboard
|
||||
10. Analytics views
|
||||
11. Advanced settings
|
||||
|
||||
---
|
||||
|
||||
**Use this document to prompt UI design tools with specific page requirements!**
|
||||
|
||||
Example prompt structure:
|
||||
```
|
||||
Create a modern dark-themed UI design for [PAGE NAME] with the following elements:
|
||||
[List specific elements from above]
|
||||
Color scheme: Purple gradient (#667eea to #764ba2)
|
||||
Style: Modern, RPG-themed, clean
|
||||
```
|
||||
401
docs/reference/UI_ELEMENTS_REFERENCE.md
Normal file
401
docs/reference/UI_ELEMENTS_REFERENCE.md
Normal file
@@ -0,0 +1,401 @@
|
||||
# UI Elements Reference - Storyteller RPG
|
||||
|
||||
**Purpose:** Complete catalog of UI elements for design system templates
|
||||
**Date:** October 12, 2025
|
||||
|
||||
---
|
||||
|
||||
## 🎨 Design System Overview
|
||||
|
||||
### Color Palette
|
||||
- **Primary:** Purple gradient (#667eea to #764ba2)
|
||||
- **Background:** Dark theme (#1a1a2e, #16213e)
|
||||
- **Success:** Green (#10b981, #86efac)
|
||||
- **Text:** White (#fff), Light gray (#aaa, #ccc)
|
||||
- **Borders:** Subtle white rgba (0.1 opacity)
|
||||
|
||||
### Typography
|
||||
- **Headings:** 24-32px, bold
|
||||
- **Body:** 14-16px, normal
|
||||
- **Small:** 12-13px, secondary info
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 1: Session Setup / Landing Page
|
||||
|
||||
### Purpose
|
||||
Entry point for creating/joining sessions and characters
|
||||
|
||||
### Key Sections
|
||||
|
||||
#### 1. Header Area
|
||||
- **App Title:** "🎭 Storyteller RPG"
|
||||
- **Subtitle:** Brief tagline
|
||||
- **Logo placeholder** (future)
|
||||
|
||||
#### 2. Demo Session Quick Access
|
||||
- **Section Title:** "🎲 Demo Session - 'The Cursed Tavern'"
|
||||
- **Description text:** Brief explanation
|
||||
- **Three action buttons:**
|
||||
- Join as Storyteller (gold gradient)
|
||||
- Play as Bargin (character 1)
|
||||
- Play as Willow (character 2)
|
||||
- **Button styling:** Large, prominent, with icons
|
||||
|
||||
#### 3. Session Creation Section
|
||||
- **Section Title:** "Create New Session"
|
||||
- **Description:** "Start a new game as the storyteller"
|
||||
- **Input field:** Session name (text)
|
||||
- **Primary button:** "Create Session"
|
||||
|
||||
#### 4. Session Join Section
|
||||
- **Section Title:** "Join Existing Session"
|
||||
- **Description:** "Play as a character in an ongoing game"
|
||||
- **Form elements:**
|
||||
- Session ID input (text)
|
||||
- Character name input (text, required)
|
||||
- Description textarea (3 rows)
|
||||
- Personality textarea (2 rows, optional)
|
||||
- Model selector (dropdown with optgroups)
|
||||
- Model hint text (small, gray)
|
||||
- **Character creation options:**
|
||||
- Primary button: "✨ Create Character (Wizard)"
|
||||
- Divider: "or"
|
||||
- Toggle button: "Quick Create" (shows simple form)
|
||||
- **Submit button:** "Join Session (Simple)" (conditional)
|
||||
|
||||
#### 5. Dividers
|
||||
- Horizontal rule with centered text ("OR")
|
||||
- Visual separation between sections
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 2: Character View (Player Perspective)
|
||||
|
||||
### Purpose
|
||||
Player's interface for interacting with storyteller
|
||||
|
||||
### Layout Structure
|
||||
Three-column layout: Info | Messages | Public Feed
|
||||
|
||||
### Key Sections
|
||||
|
||||
#### 1. Character Header
|
||||
- **Character name** (h2, white, bold)
|
||||
- **Description text** (gray, italic)
|
||||
- **Personality traits** (with emoji prefix)
|
||||
- **Profile badges** (if profile exists):
|
||||
- Race badge
|
||||
- Class badge
|
||||
- Personality type badge
|
||||
- **Action buttons:**
|
||||
- Export button (📥)
|
||||
- Connection status indicator (● Connected / ○ Disconnected)
|
||||
|
||||
#### 2. Current Scene Panel (if active)
|
||||
- **Section title:** "📜 Current Scene"
|
||||
- **Scene text** (large, prominent)
|
||||
- **Background:** Highlighted panel
|
||||
|
||||
#### 3. Public Messages Section
|
||||
- **Section title:** "📢 Public Actions (All Players See)"
|
||||
- **Message list:**
|
||||
- Message sender label
|
||||
- Timestamp
|
||||
- Message content
|
||||
- Visual distinction from private messages
|
||||
|
||||
#### 4. Private Conversation Area
|
||||
- **Section title:** "💬 Private Conversation with Storyteller"
|
||||
- **Message thread:**
|
||||
- Character messages (right-aligned, colored)
|
||||
- Storyteller messages (left-aligned, different color)
|
||||
- Timestamps
|
||||
- Message bubbles
|
||||
- **Auto-scroll to latest**
|
||||
|
||||
#### 5. Message Composer
|
||||
- **Message visibility selector** (dropdown):
|
||||
- Private
|
||||
- Public
|
||||
- Mixed
|
||||
- **Input area (varies by type):**
|
||||
- Private/Public: Single text input
|
||||
- Mixed: Two textareas (public + private)
|
||||
- **Send button** (primary, disabled when disconnected)
|
||||
|
||||
#### 6. AI Generation Section (future)
|
||||
- Generate suggestion button
|
||||
- Prompt customization
|
||||
- Regenerate option
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 3: Storyteller View (GM Perspective)
|
||||
|
||||
### Purpose
|
||||
Game master interface to manage all players and narrate story
|
||||
|
||||
### Layout Structure
|
||||
Two-column: Character list sidebar | Main content area
|
||||
|
||||
### Key Sections
|
||||
|
||||
#### 1. Session Header
|
||||
- **Session name** (h2)
|
||||
- **Session ID display** with copy button
|
||||
- **Quick copy feedback** (tooltip/toast)
|
||||
|
||||
#### 2. Character List Sidebar
|
||||
- **Section title:** "Active Characters"
|
||||
- **Character cards:**
|
||||
- Character name
|
||||
- "💬 View" button (per character)
|
||||
- Highlight active selection
|
||||
- Pending response indicator (red dot)
|
||||
- **Scrollable list**
|
||||
|
||||
#### 3. Scene Narration Panel
|
||||
- **Section title:** "📜 Scene Narration"
|
||||
- **Textarea:** Large input for scene description
|
||||
- **Buttons:**
|
||||
- "Broadcast Scene" (primary)
|
||||
- "✨ AI Suggest" (secondary, generates scene)
|
||||
|
||||
#### 4. Public Actions Feed
|
||||
- **Section title:** "📢 Recent Public Actions"
|
||||
- **Message list:**
|
||||
- Character name
|
||||
- Action content
|
||||
- Timestamp
|
||||
- **Latest 5 messages shown**
|
||||
|
||||
#### 5. Character Conversation View
|
||||
- **Header:** Selected character name
|
||||
- **Conversation thread:**
|
||||
- Character messages
|
||||
- Your responses
|
||||
- Timestamps
|
||||
- **Response composer:**
|
||||
- Large textarea
|
||||
- Button group:
|
||||
- "✨ AI Suggest"
|
||||
- "Send Private Response"
|
||||
|
||||
#### 6. Multi-Character Response (future)
|
||||
- Select multiple characters
|
||||
- Generate context-aware response
|
||||
- Broadcast to selected players
|
||||
|
||||
---
|
||||
|
||||
## 📄 Page 4: Character Creation Wizard
|
||||
|
||||
### Purpose
|
||||
6-step guided character creation with profiles
|
||||
|
||||
### Layout Structure
|
||||
Modal overlay with centered card
|
||||
|
||||
### Key Sections
|
||||
|
||||
#### 1. Wizard Header
|
||||
- **Title:** "Create Your Character"
|
||||
- **Progress indicator:**
|
||||
- 6 steps shown
|
||||
- Active step highlighted
|
||||
- Step labels visible
|
||||
|
||||
#### 2. Step Navigation
|
||||
- **Footer buttons:**
|
||||
- Cancel (left)
|
||||
- Back (if not step 1)
|
||||
- Next (steps 1-5)
|
||||
- Create Character (step 6)
|
||||
|
||||
### Step-by-Step UI Elements
|
||||
|
||||
#### Step 1: Basic Info
|
||||
- **Form elements:**
|
||||
- Name input (required)
|
||||
- Gender selector (dropdown)
|
||||
- **Import section:**
|
||||
- Hint text
|
||||
- Import from JSON button (file picker)
|
||||
|
||||
#### Step 2: Description
|
||||
- **Form elements:**
|
||||
- Description textarea (4 rows, required)
|
||||
- Background textarea (3 rows, optional)
|
||||
|
||||
#### Step 3: Race & Class
|
||||
- **Selection grids:** (2x3 or responsive)
|
||||
- Race cards (clickable)
|
||||
- Class cards (clickable)
|
||||
- **Card elements:**
|
||||
- Name (bold)
|
||||
- Description (gray)
|
||||
- Selected state (highlighted border, gradient background)
|
||||
- Hover effects
|
||||
|
||||
#### Step 4: Personality
|
||||
- **Selection grid:** 2x2
|
||||
- Personality type cards
|
||||
- Same card styling as Step 3
|
||||
- **Additional traits textarea** (optional)
|
||||
|
||||
#### Step 5: AI Model
|
||||
- **Model selector:** Large dropdown
|
||||
- Optgroups (OpenAI, OpenRouter)
|
||||
- Model names with providers
|
||||
- **Hint text:** Model personality differences
|
||||
|
||||
#### Step 6: Review
|
||||
- **Preview panels:**
|
||||
- Basic Information
|
||||
- Description
|
||||
- Background (if provided)
|
||||
- Additional Traits (if provided)
|
||||
- AI Model
|
||||
- **Summary card:**
|
||||
- Character identity statement
|
||||
- Highlighted/special styling
|
||||
|
||||
---
|
||||
|
||||
## 📄 Future Pages (Phase 3+)
|
||||
|
||||
### Gamemaster Dashboard
|
||||
- **Game creation wizard**
|
||||
- **Player slot assignment**
|
||||
- **Role management grid**
|
||||
- **Game state overview**
|
||||
- **AI control panel**
|
||||
|
||||
### Admin Panel
|
||||
- **System overview**
|
||||
- **User management**
|
||||
- **LLM configuration**
|
||||
- **Cost tracking dashboard**
|
||||
- **Analytics charts**
|
||||
|
||||
### Character Sheet (Enhanced)
|
||||
- **Stats display**
|
||||
- **Inventory grid**
|
||||
- **Skills list**
|
||||
- **Equipment slots**
|
||||
- **Character progression**
|
||||
|
||||
---
|
||||
|
||||
## 🎨 Common UI Components
|
||||
|
||||
### Buttons
|
||||
1. **Primary button:** Purple gradient, white text
|
||||
2. **Secondary button:** Transparent, border, hover effect
|
||||
3. **Wizard button:** Extra gradient styling
|
||||
4. **Export/Action buttons:** Subtle rgba background
|
||||
5. **Icon buttons:** Small, inline
|
||||
|
||||
### Form Elements
|
||||
1. **Text inputs:** Dark background, subtle border, focus glow
|
||||
2. **Textareas:** Resizable, same styling as inputs
|
||||
3. **Dropdowns:** Custom styling, optgroups
|
||||
4. **File pickers:** Hidden, triggered by styled button
|
||||
|
||||
### Cards
|
||||
1. **Selection cards:** Clickable, hover lift, selected state
|
||||
2. **Character cards:** Compact, button included
|
||||
3. **Message cards:** Bubbles, aligned left/right
|
||||
4. **Preview panels:** Bordered sections with headers
|
||||
|
||||
### Indicators
|
||||
1. **Status dots:** Colored circles (● ○)
|
||||
2. **Badges:** Rounded rectangles, colored background
|
||||
3. **Progress bars:** Step indicators
|
||||
4. **Loading states:** Spinners, skeleton screens
|
||||
|
||||
### Feedback
|
||||
1. **Toasts/Alerts:** Success/error messages
|
||||
2. **Tooltips:** Hover information
|
||||
3. **Validation messages:** Inline form errors
|
||||
4. **Empty states:** No data placeholders
|
||||
|
||||
---
|
||||
|
||||
## 📐 Layout Patterns
|
||||
|
||||
### Responsive Breakpoints
|
||||
- **Desktop:** > 768px (multi-column)
|
||||
- **Mobile:** ≤ 768px (single column, stacked)
|
||||
|
||||
### Grid Systems
|
||||
- **2-column:** Sidebar + main content
|
||||
- **3-column:** Info + center + sidebar
|
||||
- **Selection grids:** Auto-fit, min 200px
|
||||
|
||||
### Spacing
|
||||
- **Sections:** 2-3rem padding
|
||||
- **Elements:** 1-1.5rem gaps
|
||||
- **Inline:** 0.5-1rem margins
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Design Prompt Template
|
||||
|
||||
**For UI Design LLM:**
|
||||
|
||||
```
|
||||
Create a modern, dark-themed UI design for [PAGE NAME] with these elements:
|
||||
|
||||
**Color Scheme:**
|
||||
- Primary: Purple gradient (#667eea to #764ba2)
|
||||
- Background: Dark navy (#1a1a2e, #16213e)
|
||||
- Accents: White with 10% opacity borders
|
||||
- Text: White and light gray
|
||||
|
||||
**Layout:**
|
||||
[Describe specific layout]
|
||||
|
||||
**Components Needed:**
|
||||
[List specific elements for that page]
|
||||
|
||||
**Style:**
|
||||
- Modern, clean, RPG-themed
|
||||
- Smooth gradients and shadows
|
||||
- Glassmorphism effects
|
||||
- Smooth hover animations
|
||||
- Mobile responsive
|
||||
|
||||
**Inspiration:**
|
||||
Discord's UI, modern game interfaces, fantasy themes
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📊 Component Priority
|
||||
|
||||
### Essential (Implement First)
|
||||
1. Session setup forms
|
||||
2. Message display/composer
|
||||
3. Character header/info
|
||||
4. Navigation/buttons
|
||||
|
||||
### Important (Phase 2-3)
|
||||
1. Character creation wizard
|
||||
2. Storyteller dashboard
|
||||
3. Profile displays
|
||||
4. Export/import UI
|
||||
|
||||
### Nice-to-Have (Phase 4+)
|
||||
1. Character sheets with stats
|
||||
2. Inventory management
|
||||
3. Dice roller UI
|
||||
4. Image generation panels
|
||||
5. Analytics dashboards
|
||||
|
||||
---
|
||||
|
||||
**Total UI Elements Cataloged:** 100+
|
||||
**Pages Documented:** 4 (+ 3 future)
|
||||
**Ready for design system creation** ✅
|
||||
343
docs/reference/UI_QUICK_REFERENCE.md
Normal file
343
docs/reference/UI_QUICK_REFERENCE.md
Normal file
@@ -0,0 +1,343 @@
|
||||
# UI Design Quick Reference
|
||||
|
||||
**TL;DR guide for getting UI designs quickly**
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Priority Order
|
||||
|
||||
### Phase 2 (Current - Already Built)
|
||||
✅ Session Setup Page
|
||||
✅ Character View
|
||||
✅ Character Creation Wizard
|
||||
✅ Storyteller View
|
||||
|
||||
### Phase 3 (Next - Need Designs)
|
||||
🎨 Gamemaster Control Panel
|
||||
🎨 Game Creation Wizard
|
||||
🎨 Role Assignment Interface
|
||||
|
||||
### Phase 4+ (Future)
|
||||
⏳ Admin Dashboard
|
||||
⏳ Analytics Views
|
||||
|
||||
---
|
||||
|
||||
## 📄 6 Core Pages Summary
|
||||
|
||||
| Page | Purpose | Complexity | Priority |
|
||||
|------|---------|------------|----------|
|
||||
| **Session Setup** | Landing, join/create | Low | ✅ Built |
|
||||
| **Character View** | Player interface | Medium | ✅ Built |
|
||||
| **Character Wizard** | Character creation | Medium | ✅ Built |
|
||||
| **Storyteller View** | GM interface | High | ✅ Built |
|
||||
| **Gamemaster Panel** | Game management | High | 🎨 Next |
|
||||
| **Admin Dashboard** | System admin | High | ⏳ Future |
|
||||
|
||||
---
|
||||
|
||||
## 🎨 Design Files Location
|
||||
|
||||
All design documentation in `/docs/reference/`:
|
||||
- **UI_ELEMENTS_INVENTORY.md** - Complete element list by page (15,000+ words)
|
||||
- **UI_DESIGN_PROMPTS.md** - Copy-paste prompts for LLMs
|
||||
- **UI_QUICK_REFERENCE.md** - This file
|
||||
|
||||
---
|
||||
|
||||
## ⚡ Quick Start
|
||||
|
||||
### To Get Designs Fast:
|
||||
|
||||
1. **Read the prompts file:**
|
||||
- `/docs/reference/UI_DESIGN_PROMPTS.md`
|
||||
- Find the page you need
|
||||
- Copy the full prompt
|
||||
|
||||
2. **Choose your tool:**
|
||||
- **v0.dev** (Vercel) - Best for React/Tailwind code
|
||||
- **Midjourney/DALL-E** - Best for visual mockups
|
||||
- **Claude/GPT-4** - Best for HTML/CSS implementation
|
||||
|
||||
3. **Generate:**
|
||||
- Paste prompt
|
||||
- Add tool-specific instructions
|
||||
- Generate multiple variations
|
||||
- Iterate and refine
|
||||
|
||||
---
|
||||
|
||||
## 🎨 Current Design System (Already Implemented)
|
||||
|
||||
### Colors
|
||||
```css
|
||||
--primary-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--bg-dark: #1a1a2e;
|
||||
--surface-dark: #2d3748;
|
||||
--text-light: #ffffff;
|
||||
--accent-purple: #667eea;
|
||||
```
|
||||
|
||||
### Components We Have
|
||||
- ✅ Buttons (primary, secondary, icon)
|
||||
- ✅ Input fields (text, textarea, dropdown)
|
||||
- ✅ Cards (base, interactive, info)
|
||||
- ✅ Badges/Pills
|
||||
- ✅ Message bubbles
|
||||
- ✅ Selection cards (wizard)
|
||||
- ✅ Progress indicator
|
||||
- ✅ Form layouts
|
||||
- ✅ Modal overlays
|
||||
|
||||
### Components We Need
|
||||
- 🎨 Data tables
|
||||
- 🎨 Drag-and-drop cards
|
||||
- 🎨 Charts (line, bar, pie)
|
||||
- 🎨 Timeline/activity feed
|
||||
- 🎨 Tabs component
|
||||
- 🎨 Metric cards with trends
|
||||
- 🎨 Role assignment slots
|
||||
|
||||
---
|
||||
|
||||
## 📋 Example: Getting Gamemaster Panel Design
|
||||
|
||||
### Option 1: v0.dev (Code + Design)
|
||||
```
|
||||
Prompt: [Copy from UI_DESIGN_PROMPTS.md - Prompt 5]
|
||||
Add: "Generate as Next.js components with Tailwind CSS and shadcn/ui"
|
||||
Output: Working React code + visual preview
|
||||
```
|
||||
|
||||
### Option 2: Midjourney (Mockup)
|
||||
```
|
||||
Prompt: [Copy from UI_DESIGN_PROMPTS.md - Prompt 5]
|
||||
Add: "UI mockup, high fidelity, Figma style, dark theme, 4k"
|
||||
Output: Visual design to reference
|
||||
```
|
||||
|
||||
### Option 3: Manual Implementation
|
||||
```
|
||||
1. Read element list in UI_ELEMENTS_INVENTORY.md
|
||||
2. Sketch/wireframe layout
|
||||
3. Build components one by one
|
||||
4. Match existing design system colors/spacing
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🔧 Common Customizations
|
||||
|
||||
### To Match Different Styles:
|
||||
|
||||
**Sci-Fi Theme:**
|
||||
```
|
||||
Change gradient to: #00d9ff to #0099ff (cyan)
|
||||
Add: Glowing borders, neon accents
|
||||
Fonts: Orbitron or Exo 2
|
||||
```
|
||||
|
||||
**Fantasy Theme:**
|
||||
```
|
||||
Keep purple gradient
|
||||
Add: Texture overlays, paper-like cards
|
||||
Fonts: Cinzel or IM Fell
|
||||
Decorative borders
|
||||
```
|
||||
|
||||
**Minimal Theme:**
|
||||
```
|
||||
Change to monochrome: #000000 to #ffffff
|
||||
Remove: Gradients, decorative elements
|
||||
Fonts: Inter or System UI
|
||||
Flat design
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 📐 Layout Templates
|
||||
|
||||
### Dashboard Layout (Gamemaster/Admin)
|
||||
```
|
||||
┌─────────────────────────────────┐
|
||||
│ Header (Global Actions) │
|
||||
├──────┬──────────────────────────┤
|
||||
│ Nav │ Main Content Area │
|
||||
│ Bar │ │
|
||||
│ │ ┌────────┬────────┐ │
|
||||
│ │ │ Card │ Card │ │
|
||||
│ │ └────────┴────────┘ │
|
||||
│ │ │
|
||||
│ │ [Tables/Charts/Forms] │
|
||||
└──────┴──────────────────────────┘
|
||||
|
||||
Sidebar: 240px
|
||||
Content: flex-1
|
||||
Gap: 24px
|
||||
```
|
||||
|
||||
### Chat Layout (Character/Storyteller)
|
||||
```
|
||||
┌─────────────────────────────────┐
|
||||
│ Header (Info + Actions) │
|
||||
├─────────────────────────────────┤
|
||||
│ │
|
||||
│ Scrollable Message Area │
|
||||
│ (Messages stacked vertically) │
|
||||
│ │
|
||||
├─────────────────────────────────┤
|
||||
│ Fixed Composer (Bottom) │
|
||||
└─────────────────────────────────┘
|
||||
|
||||
Header: Auto height
|
||||
Messages: flex-1, overflow-auto
|
||||
Composer: Auto height, fixed position
|
||||
```
|
||||
|
||||
### Wizard Layout
|
||||
```
|
||||
┌─────────────────────────────────┐
|
||||
│ Wizard Header + Progress │
|
||||
├─────────────────────────────────┤
|
||||
│ │
|
||||
│ │
|
||||
│ Step Content (Centered) │
|
||||
│ Max Width: 600px │
|
||||
│ │
|
||||
│ │
|
||||
├─────────────────────────────────┤
|
||||
│ Footer (Cancel | Back | Next) │
|
||||
└─────────────────────────────────┘
|
||||
|
||||
Modal: Max 800px width, centered
|
||||
Content: Vertical padding 48px
|
||||
Footer: Sticky bottom
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Phase 3 Design Priorities
|
||||
|
||||
### Must Have First:
|
||||
1. **Gamemaster Dashboard** - Overview/home screen
|
||||
2. **Game Creation Form** - Simple version
|
||||
3. **Player Slot Cards** - Assignment interface
|
||||
|
||||
### Can Wait:
|
||||
4. Role drag-and-drop (use simple assignment first)
|
||||
5. Advanced analytics
|
||||
6. Detailed configuration screens
|
||||
|
||||
---
|
||||
|
||||
## 💡 Tips for Design Consistency
|
||||
|
||||
### When Designing New Pages:
|
||||
|
||||
1. **Reuse existing components**
|
||||
- Check what's already built
|
||||
- Extend rather than recreate
|
||||
|
||||
2. **Match spacing**
|
||||
- Use 8px grid system
|
||||
- Common gaps: 16px, 24px, 32px
|
||||
|
||||
3. **Follow color usage**
|
||||
- Purple for primary actions
|
||||
- Dark backgrounds (#2d3748)
|
||||
- White/light text
|
||||
|
||||
4. **Keep hierarchy clear**
|
||||
- Largest: Page titles (2rem)
|
||||
- Medium: Section titles (1.5rem)
|
||||
- Normal: Body text (1rem)
|
||||
|
||||
5. **Maintain card style**
|
||||
- Rounded 8-12px
|
||||
- Subtle shadows
|
||||
- Padding 1-2rem
|
||||
|
||||
---
|
||||
|
||||
## 📱 Responsive Breakpoints
|
||||
|
||||
```css
|
||||
/* Mobile First */
|
||||
.container {
|
||||
width: 100%;
|
||||
padding: 16px;
|
||||
}
|
||||
|
||||
/* Tablet - 768px */
|
||||
@media (min-width: 768px) {
|
||||
.container {
|
||||
padding: 24px;
|
||||
}
|
||||
.grid {
|
||||
grid-template-columns: repeat(2, 1fr);
|
||||
}
|
||||
}
|
||||
|
||||
/* Desktop - 1024px */
|
||||
@media (min-width: 1024px) {
|
||||
.container {
|
||||
max-width: 1200px;
|
||||
margin: 0 auto;
|
||||
}
|
||||
.grid {
|
||||
grid-template-columns: repeat(3, 1fr);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🚀 Workflow Recommendation
|
||||
|
||||
### For Phase 3 Implementation:
|
||||
|
||||
**Week 1:** Design Phase
|
||||
- Day 1: Generate Gamemaster dashboard mockups
|
||||
- Day 2: Review and refine designs
|
||||
- Day 3: Generate component mockups
|
||||
- Day 4: Finalize design system updates
|
||||
- Day 5: Create component specifications
|
||||
|
||||
**Week 2-3:** Implementation
|
||||
- Build reusable components
|
||||
- Implement layouts
|
||||
- Connect to backend
|
||||
- Test responsive behavior
|
||||
- Polish animations
|
||||
|
||||
**Week 4:** Polish
|
||||
- Fix edge cases
|
||||
- Accessibility improvements
|
||||
- Performance optimization
|
||||
- User testing
|
||||
|
||||
---
|
||||
|
||||
## 📚 Resources
|
||||
|
||||
### Design Tools
|
||||
- **v0.dev** - https://v0.dev (AI code generation)
|
||||
- **Figma** - https://figma.com (Design/prototype)
|
||||
- **Tailwind UI** - https://tailwindui.com (Component library)
|
||||
- **shadcn/ui** - https://ui.shadcn.com (React components)
|
||||
|
||||
### Inspiration
|
||||
- **Dribbble** - Search "RPG dashboard dark theme"
|
||||
- **Behance** - Search "game master interface"
|
||||
- **Awwwards** - Dark themed web apps
|
||||
|
||||
### Color Tools
|
||||
- **Coolors** - Generate palette variations
|
||||
- **Color Hunt** - Find complementary palettes
|
||||
- **Contrast Checker** - Ensure accessibility
|
||||
|
||||
---
|
||||
|
||||
**Everything you need to get UI designs for Phase 3 is ready!** 🎨✨
|
||||
|
||||
Start with the Gamemaster Control Panel - that's the biggest design challenge for Phase 3.
|
||||
@@ -954,6 +954,16 @@ body {
|
||||
font-size: 0.9rem;
|
||||
}
|
||||
|
||||
.public-message-character-header {
|
||||
background: #2d3748;
|
||||
padding: 1.5rem;
|
||||
border-radius: 8px 8px 0 0;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: flex-start;
|
||||
gap: 1rem;
|
||||
}
|
||||
|
||||
.public-msg-content {
|
||||
flex: 1;
|
||||
color: #2d3748;
|
||||
@@ -1223,6 +1233,75 @@ body {
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
/* Character Profile Display */
|
||||
.character-profile-summary {
|
||||
display: flex;
|
||||
gap: 0.5rem;
|
||||
margin-top: 0.5rem;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
|
||||
.profile-badge {
|
||||
background: rgba(102, 126, 234, 0.2);
|
||||
color: #667eea;
|
||||
padding: 0.25rem 0.75rem;
|
||||
border-radius: 12px;
|
||||
font-size: 0.85rem;
|
||||
font-weight: 500;
|
||||
border: 1px solid rgba(102, 126, 234, 0.3);
|
||||
}
|
||||
|
||||
.character-actions {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 0.75rem;
|
||||
align-items: flex-end;
|
||||
}
|
||||
|
||||
.btn-export {
|
||||
background: rgba(102, 126, 234, 0.2);
|
||||
color: #fff;
|
||||
border: 1px solid rgba(102, 126, 234, 0.5);
|
||||
padding: 0.5rem 1rem;
|
||||
border-radius: 6px;
|
||||
cursor: pointer;
|
||||
font-size: 0.9rem;
|
||||
transition: all 0.2s ease;
|
||||
}
|
||||
|
||||
.btn-export:hover {
|
||||
background: rgba(102, 126, 234, 0.3);
|
||||
border-color: #667eea;
|
||||
transform: translateY(-1px);
|
||||
}
|
||||
|
||||
/* Character Creation Options */
|
||||
.character-creation-options {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 1rem;
|
||||
margin-top: 1.5rem;
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
|
||||
.btn-wizard {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border: none;
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
.btn-wizard:hover {
|
||||
background: linear-gradient(135deg, #5568d3 0%, #65408b 100%);
|
||||
transform: translateY(-2px);
|
||||
box-shadow: 0 6px 20px rgba(102, 126, 234, 0.4);
|
||||
}
|
||||
|
||||
.option-divider {
|
||||
color: #718096;
|
||||
font-size: 0.9rem;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
@media (max-width: 768px) {
|
||||
.storyteller-content {
|
||||
grid-template-columns: 1fr;
|
||||
@@ -1235,4 +1314,12 @@ body {
|
||||
.message {
|
||||
max-width: 85%;
|
||||
}
|
||||
|
||||
.character-creation-options {
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.option-divider {
|
||||
margin: 0.5rem 0;
|
||||
}
|
||||
}
|
||||
|
||||
321
frontend/src/components/CharacterCreationWizard.css
Normal file
321
frontend/src/components/CharacterCreationWizard.css
Normal file
@@ -0,0 +1,321 @@
|
||||
.wizard-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background-color: rgba(0, 0, 0, 0.8);
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
z-index: 1000;
|
||||
padding: 20px;
|
||||
}
|
||||
|
||||
.wizard-container {
|
||||
background: linear-gradient(135deg, #1a1a2e 0%, #16213e 100%);
|
||||
border-radius: 15px;
|
||||
max-width: 800px;
|
||||
width: 100%;
|
||||
max-height: 90vh;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
box-shadow: 0 10px 40px rgba(0, 0, 0, 0.5);
|
||||
border: 1px solid rgba(255, 255, 255, 0.1);
|
||||
}
|
||||
|
||||
.wizard-header {
|
||||
padding: 30px;
|
||||
border-bottom: 1px solid rgba(255, 255, 255, 0.1);
|
||||
}
|
||||
|
||||
.wizard-header h2 {
|
||||
margin: 0 0 20px 0;
|
||||
color: #fff;
|
||||
font-size: 28px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.wizard-progress {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
gap: 10px;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
|
||||
.progress-step {
|
||||
flex: 1;
|
||||
min-width: 100px;
|
||||
padding: 10px;
|
||||
background: rgba(255, 255, 255, 0.05);
|
||||
border-radius: 8px;
|
||||
text-align: center;
|
||||
font-size: 12px;
|
||||
color: #888;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.progress-step.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
color: #fff;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.wizard-content {
|
||||
flex: 1;
|
||||
overflow-y: auto;
|
||||
padding: 30px;
|
||||
}
|
||||
|
||||
.wizard-step {
|
||||
animation: fadeIn 0.3s ease;
|
||||
}
|
||||
|
||||
@keyframes fadeIn {
|
||||
from { opacity: 0; transform: translateY(10px); }
|
||||
to { opacity: 1; transform: translateY(0); }
|
||||
}
|
||||
|
||||
.wizard-step h3 {
|
||||
margin: 0 0 25px 0;
|
||||
color: #fff;
|
||||
font-size: 22px;
|
||||
}
|
||||
|
||||
.form-group {
|
||||
margin-bottom: 25px;
|
||||
}
|
||||
|
||||
.form-group label {
|
||||
display: block;
|
||||
margin-bottom: 8px;
|
||||
color: #aaa;
|
||||
font-weight: 500;
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
.form-group input[type="text"],
|
||||
.form-group textarea,
|
||||
.form-group select {
|
||||
width: 100%;
|
||||
padding: 12px;
|
||||
background: rgba(255, 255, 255, 0.05);
|
||||
border: 1px solid rgba(255, 255, 255, 0.1);
|
||||
border-radius: 8px;
|
||||
color: #fff;
|
||||
font-size: 14px;
|
||||
font-family: inherit;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.form-group input[type="text"]:focus,
|
||||
.form-group textarea:focus,
|
||||
.form-group select:focus {
|
||||
outline: none;
|
||||
border-color: #667eea;
|
||||
background: rgba(102, 126, 234, 0.1);
|
||||
}
|
||||
|
||||
.form-group textarea {
|
||||
resize: vertical;
|
||||
min-height: 80px;
|
||||
}
|
||||
|
||||
.selection-grid {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
|
||||
gap: 15px;
|
||||
margin-top: 15px;
|
||||
}
|
||||
|
||||
.selection-card {
|
||||
padding: 20px;
|
||||
background: rgba(255, 255, 255, 0.05);
|
||||
border: 2px solid rgba(255, 255, 255, 0.1);
|
||||
border-radius: 10px;
|
||||
cursor: pointer;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.selection-card:hover {
|
||||
background: rgba(255, 255, 255, 0.08);
|
||||
border-color: rgba(102, 126, 234, 0.5);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.selection-card.selected {
|
||||
background: linear-gradient(135deg, rgba(102, 126, 234, 0.2) 0%, rgba(118, 75, 162, 0.2) 100%);
|
||||
border-color: #667eea;
|
||||
box-shadow: 0 4px 15px rgba(102, 126, 234, 0.3);
|
||||
}
|
||||
|
||||
.selection-name {
|
||||
font-size: 16px;
|
||||
font-weight: bold;
|
||||
color: #fff;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.selection-desc {
|
||||
font-size: 13px;
|
||||
color: #aaa;
|
||||
line-height: 1.4;
|
||||
}
|
||||
|
||||
.import-section {
|
||||
margin-top: 30px;
|
||||
padding: 20px;
|
||||
background: rgba(102, 126, 234, 0.1);
|
||||
border: 1px dashed rgba(102, 126, 234, 0.3);
|
||||
border-radius: 10px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.import-hint {
|
||||
margin: 0 0 10px 0;
|
||||
color: #aaa;
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
.btn-import {
|
||||
display: inline-block;
|
||||
padding: 10px 20px;
|
||||
background: rgba(102, 126, 234, 0.2);
|
||||
border: 1px solid #667eea;
|
||||
border-radius: 8px;
|
||||
color: #fff;
|
||||
cursor: pointer;
|
||||
transition: all 0.3s ease;
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
.btn-import:hover {
|
||||
background: rgba(102, 126, 234, 0.3);
|
||||
transform: translateY(-1px);
|
||||
}
|
||||
|
||||
.model-select-large {
|
||||
padding: 15px !important;
|
||||
font-size: 15px !important;
|
||||
}
|
||||
|
||||
.model-hint {
|
||||
margin-top: 10px;
|
||||
font-size: 13px;
|
||||
color: #aaa;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.character-preview {
|
||||
background: rgba(255, 255, 255, 0.03);
|
||||
border-radius: 10px;
|
||||
padding: 20px;
|
||||
}
|
||||
|
||||
.preview-section {
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 20px;
|
||||
border-bottom: 1px solid rgba(255, 255, 255, 0.1);
|
||||
}
|
||||
|
||||
.preview-section:last-child {
|
||||
border-bottom: none;
|
||||
margin-bottom: 0;
|
||||
padding-bottom: 0;
|
||||
}
|
||||
|
||||
.preview-section h4 {
|
||||
margin: 0 0 10px 0;
|
||||
color: #667eea;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.preview-section p {
|
||||
margin: 5px 0;
|
||||
color: #ccc;
|
||||
line-height: 1.6;
|
||||
}
|
||||
|
||||
.preview-section strong {
|
||||
color: #fff;
|
||||
margin-right: 5px;
|
||||
}
|
||||
|
||||
.preview-summary {
|
||||
margin-top: 20px;
|
||||
padding: 20px;
|
||||
background: linear-gradient(135deg, rgba(102, 126, 234, 0.2) 0%, rgba(118, 75, 162, 0.2) 100%);
|
||||
border-radius: 10px;
|
||||
border: 1px solid rgba(102, 126, 234, 0.3);
|
||||
}
|
||||
|
||||
.preview-summary h4 {
|
||||
margin: 0 0 10px 0;
|
||||
color: #fff;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.summary-text {
|
||||
font-size: 16px;
|
||||
color: #fff;
|
||||
line-height: 1.6;
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
.wizard-footer {
|
||||
padding: 20px 30px;
|
||||
border-top: 1px solid rgba(255, 255, 255, 0.1);
|
||||
}
|
||||
|
||||
.wizard-actions {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.wizard-navigation {
|
||||
display: flex;
|
||||
gap: 10px;
|
||||
}
|
||||
|
||||
.wizard-loading {
|
||||
padding: 50px;
|
||||
text-align: center;
|
||||
color: #aaa;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
/* Responsive */
|
||||
@media (max-width: 768px) {
|
||||
.wizard-container {
|
||||
max-width: 100%;
|
||||
max-height: 100vh;
|
||||
border-radius: 0;
|
||||
}
|
||||
|
||||
.wizard-progress {
|
||||
gap: 5px;
|
||||
}
|
||||
|
||||
.progress-step {
|
||||
min-width: 60px;
|
||||
padding: 8px 5px;
|
||||
font-size: 10px;
|
||||
}
|
||||
|
||||
.selection-grid {
|
||||
grid-template-columns: 1fr;
|
||||
}
|
||||
|
||||
.wizard-content {
|
||||
padding: 20px;
|
||||
}
|
||||
|
||||
.wizard-header {
|
||||
padding: 20px;
|
||||
}
|
||||
|
||||
.wizard-header h2 {
|
||||
font-size: 22px;
|
||||
}
|
||||
}
|
||||
389
frontend/src/components/CharacterCreationWizard.js
Normal file
389
frontend/src/components/CharacterCreationWizard.js
Normal file
@@ -0,0 +1,389 @@
|
||||
import React, { useState, useEffect } from 'react';
|
||||
import './CharacterCreationWizard.css';
|
||||
|
||||
const API_URL = 'http://localhost:8000';
|
||||
|
||||
function CharacterCreationWizard({ sessionId, onCharacterCreated, onCancel }) {
|
||||
const [step, setStep] = useState(1);
|
||||
const [profileOptions, setProfileOptions] = useState(null);
|
||||
const [availableModels, setAvailableModels] = useState({ openai: [], openrouter: [] });
|
||||
|
||||
// Character data
|
||||
const [characterData, setCharacterData] = useState({
|
||||
name: '',
|
||||
description: '',
|
||||
personality: '',
|
||||
llm_model: 'gpt-3.5-turbo',
|
||||
profile: {
|
||||
gender: 'Male',
|
||||
race: 'Human',
|
||||
character_class: 'Warrior',
|
||||
personality_type: 'Friendly',
|
||||
background: '',
|
||||
avatar_data: null
|
||||
}
|
||||
});
|
||||
|
||||
useEffect(() => {
|
||||
// Fetch profile options
|
||||
fetch(`${API_URL}/profile/options`)
|
||||
.then(res => res.json())
|
||||
.then(data => setProfileOptions(data))
|
||||
.catch(err => console.error('Error fetching profile options:', err));
|
||||
|
||||
// Fetch available models
|
||||
fetch(`${API_URL}/models`)
|
||||
.then(res => res.json())
|
||||
.then(data => {
|
||||
setAvailableModels(data);
|
||||
if (data.openai.length > 0) {
|
||||
updateCharacterData('llm_model', data.openai[0].id);
|
||||
} else if (data.openrouter.length > 0) {
|
||||
updateCharacterData('llm_model', data.openrouter[0].id);
|
||||
}
|
||||
})
|
||||
.catch(err => console.error('Error fetching models:', err));
|
||||
}, []);
|
||||
|
||||
const updateCharacterData = (field, value) => {
|
||||
setCharacterData(prev => ({ ...prev, [field]: value }));
|
||||
};
|
||||
|
||||
const updateProfile = (field, value) => {
|
||||
setCharacterData(prev => ({
|
||||
...prev,
|
||||
profile: { ...prev.profile, [field]: value }
|
||||
}));
|
||||
};
|
||||
|
||||
const handleNext = () => {
|
||||
if (step === 1 && !characterData.name.trim()) {
|
||||
alert('Please enter a character name');
|
||||
return;
|
||||
}
|
||||
if (step === 2 && !characterData.description.trim()) {
|
||||
alert('Please enter a character description');
|
||||
return;
|
||||
}
|
||||
setStep(step + 1);
|
||||
};
|
||||
|
||||
const handleBack = () => {
|
||||
setStep(step - 1);
|
||||
};
|
||||
|
||||
const handleCreate = async () => {
|
||||
try {
|
||||
const response = await fetch(`${API_URL}/sessions/${sessionId}/characters/`, {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
body: JSON.stringify(characterData),
|
||||
});
|
||||
|
||||
if (!response.ok) {
|
||||
throw new Error('Failed to create character');
|
||||
}
|
||||
|
||||
const character = await response.json();
|
||||
onCharacterCreated(character);
|
||||
} catch (error) {
|
||||
console.error('Error creating character:', error);
|
||||
alert('Failed to create character: ' + error.message);
|
||||
}
|
||||
};
|
||||
|
||||
const handleImport = async (event) => {
|
||||
const file = event.target.files[0];
|
||||
if (!file) return;
|
||||
|
||||
try {
|
||||
const text = await file.text();
|
||||
const importedData = JSON.parse(text);
|
||||
|
||||
// Extract character data
|
||||
const charData = importedData.character || importedData;
|
||||
|
||||
// Update form with imported data
|
||||
setCharacterData({
|
||||
name: charData.name || '',
|
||||
description: charData.description || '',
|
||||
personality: charData.personality || '',
|
||||
llm_model: charData.llm_model || 'gpt-3.5-turbo',
|
||||
profile: charData.profile || characterData.profile
|
||||
});
|
||||
|
||||
setStep(1); // Go to first step to review
|
||||
alert('Character imported! Review and modify as needed.');
|
||||
} catch (error) {
|
||||
console.error('Error importing character:', error);
|
||||
alert('Failed to import character. Please check the file format.');
|
||||
}
|
||||
};
|
||||
|
||||
if (!profileOptions) {
|
||||
return <div className="wizard-loading">Loading character creation wizard...</div>;
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="wizard-overlay">
|
||||
<div className="wizard-container">
|
||||
<div className="wizard-header">
|
||||
<h2>Create Your Character</h2>
|
||||
<div className="wizard-progress">
|
||||
<div className={`progress-step ${step >= 1 ? 'active' : ''}`}>1. Basic Info</div>
|
||||
<div className={`progress-step ${step >= 2 ? 'active' : ''}`}>2. Description</div>
|
||||
<div className={`progress-step ${step >= 3 ? 'active' : ''}`}>3. Race & Class</div>
|
||||
<div className={`progress-step ${step >= 4 ? 'active' : ''}`}>4. Personality</div>
|
||||
<div className={`progress-step ${step >= 5 ? 'active' : ''}`}>5. AI Model</div>
|
||||
<div className={`progress-step ${step >= 6 ? 'active' : ''}`}>6. Review</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="wizard-content">
|
||||
{/* Step 1: Basic Info */}
|
||||
{step === 1 && (
|
||||
<div className="wizard-step">
|
||||
<h3>Basic Information</h3>
|
||||
<div className="form-group">
|
||||
<label>Character Name *</label>
|
||||
<input
|
||||
type="text"
|
||||
value={characterData.name}
|
||||
onChange={(e) => updateCharacterData('name', e.target.value)}
|
||||
placeholder="Enter your character's name"
|
||||
autoFocus
|
||||
/>
|
||||
</div>
|
||||
<div className="form-group">
|
||||
<label>Gender</label>
|
||||
<select
|
||||
value={characterData.profile.gender}
|
||||
onChange={(e) => updateProfile('gender', e.target.value)}
|
||||
>
|
||||
{profileOptions.genders.map(gender => (
|
||||
<option key={gender} value={gender}>{gender}</option>
|
||||
))}
|
||||
</select>
|
||||
</div>
|
||||
<div className="import-section">
|
||||
<p className="import-hint">💡 Have an existing character?</p>
|
||||
<label className="btn-import">
|
||||
📥 Import from JSON
|
||||
<input
|
||||
type="file"
|
||||
accept=".json"
|
||||
onChange={handleImport}
|
||||
style={{ display: 'none' }}
|
||||
/>
|
||||
</label>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Step 2: Description */}
|
||||
{step === 2 && (
|
||||
<div className="wizard-step">
|
||||
<h3>Character Description</h3>
|
||||
<div className="form-group">
|
||||
<label>Description *</label>
|
||||
<textarea
|
||||
value={characterData.description}
|
||||
onChange={(e) => updateCharacterData('description', e.target.value)}
|
||||
placeholder="Describe your character (e.g., A brave knight seeking redemption)"
|
||||
rows="4"
|
||||
autoFocus
|
||||
/>
|
||||
</div>
|
||||
<div className="form-group">
|
||||
<label>Background Story (Optional)</label>
|
||||
<textarea
|
||||
value={characterData.profile.background}
|
||||
onChange={(e) => updateProfile('background', e.target.value)}
|
||||
placeholder="Additional background or backstory"
|
||||
rows="3"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Step 3: Race & Class */}
|
||||
{step === 3 && (
|
||||
<div className="wizard-step">
|
||||
<h3>Race & Class</h3>
|
||||
<div className="form-group">
|
||||
<label>Race</label>
|
||||
<div className="selection-grid">
|
||||
{profileOptions.races.map(race => (
|
||||
<div
|
||||
key={race}
|
||||
className={`selection-card ${characterData.profile.race === race ? 'selected' : ''}`}
|
||||
onClick={() => updateProfile('race', race)}
|
||||
>
|
||||
<div className="selection-name">{race}</div>
|
||||
<div className="selection-desc">{profileOptions.race_descriptions[race]}</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
<div className="form-group">
|
||||
<label>Class</label>
|
||||
<div className="selection-grid">
|
||||
{profileOptions.classes.map(cls => (
|
||||
<div
|
||||
key={cls}
|
||||
className={`selection-card ${characterData.profile.character_class === cls ? 'selected' : ''}`}
|
||||
onClick={() => updateProfile('character_class', cls)}
|
||||
>
|
||||
<div className="selection-name">{cls}</div>
|
||||
<div className="selection-desc">{profileOptions.class_descriptions[cls]}</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Step 4: Personality */}
|
||||
{step === 4 && (
|
||||
<div className="wizard-step">
|
||||
<h3>Personality Type</h3>
|
||||
<div className="form-group">
|
||||
<label>Choose a personality that defines your character's behavior</label>
|
||||
<div className="selection-grid">
|
||||
{profileOptions.personality_types.map(personality => (
|
||||
<div
|
||||
key={personality}
|
||||
className={`selection-card ${characterData.profile.personality_type === personality ? 'selected' : ''}`}
|
||||
onClick={() => updateProfile('personality_type', personality)}
|
||||
>
|
||||
<div className="selection-name">{personality}</div>
|
||||
<div className="selection-desc">{profileOptions.personality_descriptions[personality]}</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
<div className="form-group">
|
||||
<label>Additional Personality Traits (Optional)</label>
|
||||
<textarea
|
||||
value={characterData.personality}
|
||||
onChange={(e) => updateCharacterData('personality', e.target.value)}
|
||||
placeholder="Any additional personality traits or quirks"
|
||||
rows="3"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Step 5: AI Model */}
|
||||
{step === 5 && (
|
||||
<div className="wizard-step">
|
||||
<h3>AI Model Selection</h3>
|
||||
<div className="form-group">
|
||||
<label>Choose the AI model for this character</label>
|
||||
<select
|
||||
value={characterData.llm_model}
|
||||
onChange={(e) => updateCharacterData('llm_model', e.target.value)}
|
||||
className="model-select-large"
|
||||
>
|
||||
{availableModels.openai.length > 0 && (
|
||||
<optgroup label="OpenAI Models">
|
||||
{availableModels.openai.map(model => (
|
||||
<option key={model.id} value={model.id}>
|
||||
{model.name}
|
||||
</option>
|
||||
))}
|
||||
</optgroup>
|
||||
)}
|
||||
{availableModels.openrouter.length > 0 && (
|
||||
<optgroup label="OpenRouter Models">
|
||||
{availableModels.openrouter.map(model => (
|
||||
<option key={model.id} value={model.id}>
|
||||
{model.name} ({model.provider})
|
||||
</option>
|
||||
))}
|
||||
</optgroup>
|
||||
)}
|
||||
</select>
|
||||
<p className="model-hint">
|
||||
💡 Different models give different personalities! Try Claude for creative responses,
|
||||
GPT-4 for detailed reasoning, or Llama for faster interactions.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Step 6: Review */}
|
||||
{step === 6 && (
|
||||
<div className="wizard-step">
|
||||
<h3>Review Your Character</h3>
|
||||
<div className="character-preview">
|
||||
<div className="preview-section">
|
||||
<h4>Basic Information</h4>
|
||||
<p><strong>Name:</strong> {characterData.name}</p>
|
||||
<p><strong>Gender:</strong> {characterData.profile.gender}</p>
|
||||
<p><strong>Race:</strong> {characterData.profile.race}</p>
|
||||
<p><strong>Class:</strong> {characterData.profile.character_class}</p>
|
||||
<p><strong>Personality:</strong> {characterData.profile.personality_type}</p>
|
||||
</div>
|
||||
<div className="preview-section">
|
||||
<h4>Description</h4>
|
||||
<p>{characterData.description}</p>
|
||||
</div>
|
||||
{characterData.profile.background && (
|
||||
<div className="preview-section">
|
||||
<h4>Background</h4>
|
||||
<p>{characterData.profile.background}</p>
|
||||
</div>
|
||||
)}
|
||||
{characterData.personality && (
|
||||
<div className="preview-section">
|
||||
<h4>Additional Traits</h4>
|
||||
<p>{characterData.personality}</p>
|
||||
</div>
|
||||
)}
|
||||
<div className="preview-section">
|
||||
<h4>AI Model</h4>
|
||||
<p>{characterData.llm_model}</p>
|
||||
</div>
|
||||
<div className="preview-summary">
|
||||
<h4>Character Summary</h4>
|
||||
<p className="summary-text">
|
||||
{characterData.name} is a {characterData.profile.gender.toLowerCase()} {characterData.profile.race} {characterData.profile.character_class} with a {characterData.profile.personality_type.toLowerCase()} personality.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
|
||||
<div className="wizard-footer">
|
||||
<div className="wizard-actions">
|
||||
<button className="btn-secondary" onClick={onCancel}>
|
||||
Cancel
|
||||
</button>
|
||||
<div className="wizard-navigation">
|
||||
{step > 1 && (
|
||||
<button className="btn-secondary" onClick={handleBack}>
|
||||
← Back
|
||||
</button>
|
||||
)}
|
||||
{step < 6 ? (
|
||||
<button className="btn-primary" onClick={handleNext}>
|
||||
Next →
|
||||
</button>
|
||||
) : (
|
||||
<button className="btn-primary" onClick={handleCreate}>
|
||||
✨ Create Character
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export default CharacterCreationWizard;
|
||||
@@ -16,6 +16,30 @@ function CharacterView({ sessionId, characterId }) {
|
||||
const wsRef = useRef(null);
|
||||
const messagesEndRef = useRef(null);
|
||||
|
||||
const handleExportCharacter = async () => {
|
||||
try {
|
||||
const response = await fetch(`${API_URL}/sessions/${sessionId}/characters/${characterId}/export`);
|
||||
const data = await response.json();
|
||||
|
||||
// Create download link
|
||||
const dataStr = JSON.stringify(data, null, 2);
|
||||
const dataBlob = new Blob([dataStr], { type: 'application/json' });
|
||||
const url = URL.createObjectURL(dataBlob);
|
||||
const link = document.createElement('a');
|
||||
link.href = url;
|
||||
link.download = `${characterInfo?.name || 'character'}_${new Date().toISOString().split('T')[0]}.json`;
|
||||
document.body.appendChild(link);
|
||||
link.click();
|
||||
document.body.removeChild(link);
|
||||
URL.revokeObjectURL(url);
|
||||
|
||||
alert('Character exported successfully!');
|
||||
} catch (error) {
|
||||
console.error('Error exporting character:', error);
|
||||
alert('Failed to export character');
|
||||
}
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
// Fetch character info
|
||||
fetch(`${API_URL}/sessions/${sessionId}/characters/${characterId}/conversation`)
|
||||
@@ -109,8 +133,18 @@ function CharacterView({ sessionId, characterId }) {
|
||||
{characterInfo?.personality && (
|
||||
<p className="character-personality">🎭 {characterInfo.personality}</p>
|
||||
)}
|
||||
{characterInfo?.profile && (
|
||||
<div className="character-profile-summary">
|
||||
<span className="profile-badge">{characterInfo.profile.race}</span>
|
||||
<span className="profile-badge">{characterInfo.profile.character_class}</span>
|
||||
<span className="profile-badge">{characterInfo.profile.personality_type}</span>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
<div className="connection-status">
|
||||
<div className="character-actions">
|
||||
<button className="btn-export" onClick={handleExportCharacter} title="Export character">
|
||||
📥 Export
|
||||
</button>
|
||||
<span className={`status-indicator ${isConnected ? 'connected' : 'disconnected'}`}>
|
||||
{isConnected ? '● Connected' : '○ Disconnected'}
|
||||
</span>
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import React, { useState, useEffect } from 'react';
|
||||
import CharacterCreationWizard from './CharacterCreationWizard';
|
||||
|
||||
const API_URL = 'http://localhost:8000';
|
||||
|
||||
@@ -10,6 +11,8 @@ function SessionSetup({ onCreateSession, onJoinSession }) {
|
||||
const [characterPersonality, setCharacterPersonality] = useState('');
|
||||
const [selectedModel, setSelectedModel] = useState('gpt-3.5-turbo');
|
||||
const [availableModels, setAvailableModels] = useState({ openai: [], openrouter: [] });
|
||||
const [showWizard, setShowWizard] = useState(false);
|
||||
const [useSimpleMode, setUseSimpleMode] = useState(false);
|
||||
|
||||
useEffect(() => {
|
||||
// Fetch available models
|
||||
@@ -66,7 +69,7 @@ function SessionSetup({ onCreateSession, onJoinSession }) {
|
||||
llm_model: selectedModel,
|
||||
});
|
||||
|
||||
const charResponse = await fetch(`${API_URL}/sessions/${joinSessionId}/characters/?${params}`, {
|
||||
const charResponse = await fetch(`${API_URL}/sessions/${joinSessionId}/characters/legacy/?${params}`, {
|
||||
method: 'POST',
|
||||
});
|
||||
|
||||
@@ -78,6 +81,19 @@ function SessionSetup({ onCreateSession, onJoinSession }) {
|
||||
}
|
||||
};
|
||||
|
||||
const handleCharacterCreated = (character) => {
|
||||
setShowWizard(false);
|
||||
onJoinSession(joinSessionId, character.id);
|
||||
};
|
||||
|
||||
const openWizard = () => {
|
||||
if (!joinSessionId.trim()) {
|
||||
alert('Please enter a Session ID first');
|
||||
return;
|
||||
}
|
||||
setShowWizard(true);
|
||||
};
|
||||
|
||||
// Quick join demo session functions
|
||||
const joinDemoStoryteller = () => {
|
||||
onCreateSession("demo-session-001");
|
||||
@@ -144,6 +160,15 @@ function SessionSetup({ onCreateSession, onJoinSession }) {
|
||||
<div className="setup-section">
|
||||
<h2>Join Existing Session</h2>
|
||||
<p className="section-description">Play as a character in an ongoing game</p>
|
||||
|
||||
{showWizard && (
|
||||
<CharacterCreationWizard
|
||||
sessionId={joinSessionId}
|
||||
onCharacterCreated={handleCharacterCreated}
|
||||
onCancel={() => setShowWizard(false)}
|
||||
/>
|
||||
)}
|
||||
|
||||
<div className="input-group">
|
||||
<input
|
||||
type="text"
|
||||
@@ -202,9 +227,21 @@ function SessionSetup({ onCreateSession, onJoinSession }) {
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<button className="btn-primary" onClick={joinSession}>
|
||||
Join Session
|
||||
</button>
|
||||
<div className="character-creation-options">
|
||||
<button className="btn-primary btn-wizard" onClick={openWizard}>
|
||||
✨ Create Character (Wizard)
|
||||
</button>
|
||||
<span className="option-divider">or</span>
|
||||
<button className="btn-secondary" onClick={() => setUseSimpleMode(!useSimpleMode)}>
|
||||
{useSimpleMode ? '↑ Hide' : '↓ Quick Create'}
|
||||
</button>
|
||||
</div>
|
||||
|
||||
{useSimpleMode && (
|
||||
<button className="btn-primary" onClick={joinSession}>
|
||||
Join Session (Simple)
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
214
main.py
214
main.py
@@ -42,11 +42,21 @@ class Message(BaseModel):
|
||||
public_content: Optional[str] = None # For mixed messages - visible to all
|
||||
private_content: Optional[str] = None # For mixed messages - only storyteller sees
|
||||
|
||||
class CharacterProfile(BaseModel):
|
||||
"""Character profile with race, class, gender, and personality traits"""
|
||||
gender: str = "Male" # Male, Female, Non-binary, Custom
|
||||
race: str = "Human" # Human, Elf, Dwarf, Orc, Halfling
|
||||
character_class: str = "Warrior" # Warrior, Wizard, Cleric, Archer, Rogue
|
||||
personality_type: str = "Friendly" # Friendly, Serious, Doubtful, Measured
|
||||
background: str = "" # Custom background story
|
||||
avatar_data: Optional[str] = None # base64 encoded avatar image
|
||||
|
||||
class Character(BaseModel):
|
||||
id: str = Field(default_factory=lambda: str(uuid.uuid4()))
|
||||
name: str
|
||||
description: str
|
||||
personality: str = "" # Additional personality traits
|
||||
personality: str = "" # Additional personality traits (legacy field)
|
||||
profile: Optional[CharacterProfile] = None # Structured profile
|
||||
llm_model: str = "gpt-3.5-turbo" # LLM model for this character
|
||||
conversation_history: List[Message] = [] # Private conversation with storyteller
|
||||
pending_response: bool = False # Waiting for storyteller response
|
||||
@@ -63,6 +73,61 @@ class GameSession(BaseModel):
|
||||
scene_history: List[str] = [] # All scenes narrated
|
||||
public_messages: List[Message] = [] # Public messages visible to all characters
|
||||
|
||||
# Character Profile Prompt Templates
|
||||
RACE_PROMPTS = {
|
||||
"Human": "You are a human character, versatile and adaptable to any situation. You have a balanced approach to problem-solving.",
|
||||
"Elf": "You are an elf, graceful and wise with centuries of experience. You have keen senses and a deep connection to nature and magic.",
|
||||
"Dwarf": "You are a dwarf, stout and honorable with deep knowledge of stone and metal. You are loyal, practical, and value tradition.",
|
||||
"Orc": "You are an orc, powerful and direct with a strong sense of honor and combat prowess. You value strength and straightforward action.",
|
||||
"Halfling": "You are a halfling, small but brave with natural luck and a cheerful disposition. You are resourceful and enjoy the simple pleasures of life."
|
||||
}
|
||||
|
||||
CLASS_PROMPTS = {
|
||||
"Warrior": "You excel in physical combat and tactics, preferring direct action and protecting your allies. You are brave and decisive in battle.",
|
||||
"Wizard": "You are a master of arcane arts, solving problems with magic and knowledge. You are intellectual, curious, and often seek understanding before action.",
|
||||
"Cleric": "You channel divine power to heal and protect, guided by faith and compassion. You support your allies and seek to help those in need.",
|
||||
"Archer": "You are a skilled marksman, preferring distance and precision in combat. You are patient, observant, and value accuracy over brute force.",
|
||||
"Rogue": "You rely on stealth and cunning, using tricks and skills to overcome obstacles. You are clever, adaptable, and often find unconventional solutions."
|
||||
}
|
||||
|
||||
PERSONALITY_PROMPTS = {
|
||||
"Friendly": "You are friendly and approachable, always looking for the good in others. You prefer cooperation and building positive relationships.",
|
||||
"Serious": "You are serious and focused, prioritizing efficiency and practical solutions. You are disciplined and value getting things done.",
|
||||
"Doubtful": "You are cautious and skeptical, questioning motives and analyzing situations carefully. You prefer to be prepared for potential threats.",
|
||||
"Measured": "You are measured and thoughtful, weighing options carefully before acting. You seek balance and consider multiple perspectives."
|
||||
}
|
||||
|
||||
def build_character_system_prompt(character: Character) -> str:
|
||||
"""Build system prompt from character profile"""
|
||||
if not character.profile:
|
||||
# Legacy character without profile
|
||||
base_prompt = f"You are {character.name}. {character.description}"
|
||||
if character.personality:
|
||||
base_prompt += f" {character.personality}"
|
||||
return base_prompt
|
||||
|
||||
# Build prompt from profile
|
||||
profile = character.profile
|
||||
race_trait = RACE_PROMPTS.get(profile.race, "")
|
||||
class_trait = CLASS_PROMPTS.get(profile.character_class, "")
|
||||
personality_trait = PERSONALITY_PROMPTS.get(profile.personality_type, "")
|
||||
|
||||
prompt_parts = [
|
||||
f"You are {character.name}, a {profile.gender.lower()} {profile.race} {profile.character_class}.",
|
||||
character.description,
|
||||
race_trait,
|
||||
class_trait,
|
||||
personality_trait,
|
||||
]
|
||||
|
||||
if profile.background:
|
||||
prompt_parts.append(f"Background: {profile.background}")
|
||||
|
||||
if character.personality: # Legacy personality field
|
||||
prompt_parts.append(character.personality)
|
||||
|
||||
return " ".join(filter(None, prompt_parts))
|
||||
|
||||
# In-memory storage (replace with database in production)
|
||||
sessions: Dict[str, GameSession] = {}
|
||||
|
||||
@@ -98,22 +163,27 @@ async def get_session(session_id: str):
|
||||
raise HTTPException(status_code=404, detail="Session not found")
|
||||
return sessions[session_id]
|
||||
|
||||
class CreateCharacterRequest(BaseModel):
|
||||
name: str
|
||||
description: str
|
||||
personality: str = "" # Legacy field
|
||||
llm_model: str = "gpt-3.5-turbo"
|
||||
profile: Optional[CharacterProfile] = None
|
||||
|
||||
@app.post("/sessions/{session_id}/characters/")
|
||||
async def add_character(
|
||||
session_id: str,
|
||||
name: str,
|
||||
description: str,
|
||||
personality: str = "",
|
||||
llm_model: str = "gpt-3.5-turbo"
|
||||
request: CreateCharacterRequest
|
||||
):
|
||||
if session_id not in sessions:
|
||||
raise HTTPException(status_code=404, detail="Session not found")
|
||||
|
||||
character = Character(
|
||||
name=name,
|
||||
description=description,
|
||||
personality=personality,
|
||||
llm_model=llm_model
|
||||
name=request.name,
|
||||
description=request.description,
|
||||
personality=request.personality,
|
||||
profile=request.profile,
|
||||
llm_model=request.llm_model
|
||||
)
|
||||
session = sessions[session_id]
|
||||
session.characters[character.id] = character
|
||||
@@ -127,12 +197,128 @@ async def add_character(
|
||||
"id": character.id,
|
||||
"name": character.name,
|
||||
"description": character.description,
|
||||
"llm_model": character.llm_model
|
||||
"llm_model": character.llm_model,
|
||||
"profile": character.profile.dict() if character.profile else None
|
||||
}
|
||||
})
|
||||
|
||||
return character
|
||||
|
||||
# Legacy endpoint for backward compatibility
|
||||
@app.post("/sessions/{session_id}/characters/legacy/")
|
||||
async def add_character_legacy(
|
||||
session_id: str,
|
||||
name: str,
|
||||
description: str,
|
||||
personality: str = "",
|
||||
llm_model: str = "gpt-3.5-turbo"
|
||||
):
|
||||
request = CreateCharacterRequest(
|
||||
name=name,
|
||||
description=description,
|
||||
personality=personality,
|
||||
llm_model=llm_model
|
||||
)
|
||||
return await add_character(session_id, request)
|
||||
|
||||
# Export character to JSON
|
||||
@app.get("/sessions/{session_id}/characters/{character_id}/export")
|
||||
async def export_character(session_id: str, character_id: str):
|
||||
"""Export character profile to JSON"""
|
||||
if session_id not in sessions:
|
||||
raise HTTPException(status_code=404, detail="Session not found")
|
||||
|
||||
session = sessions[session_id]
|
||||
if character_id not in session.characters:
|
||||
raise HTTPException(status_code=404, detail="Character not found")
|
||||
|
||||
character = session.characters[character_id]
|
||||
|
||||
export_data = {
|
||||
"version": "1.0",
|
||||
"character": character.model_dump(),
|
||||
"created_at": datetime.now().isoformat(),
|
||||
"export_type": "storyteller_rpg_character"
|
||||
}
|
||||
|
||||
return export_data
|
||||
|
||||
# Import character from JSON
|
||||
class ImportCharacterRequest(BaseModel):
|
||||
character_data: dict
|
||||
|
||||
@app.post("/sessions/{session_id}/characters/import")
|
||||
async def import_character(session_id: str, request: ImportCharacterRequest):
|
||||
"""Import character from exported JSON"""
|
||||
if session_id not in sessions:
|
||||
raise HTTPException(status_code=404, detail="Session not found")
|
||||
|
||||
try:
|
||||
# Validate and extract character data
|
||||
char_data = request.character_data
|
||||
if "character" in char_data:
|
||||
char_data = char_data["character"]
|
||||
|
||||
# Create character from imported data
|
||||
character = Character(**char_data)
|
||||
# Generate new ID to avoid conflicts
|
||||
character.id = str(uuid.uuid4())
|
||||
# Clear conversation history
|
||||
character.conversation_history = []
|
||||
character.pending_response = False
|
||||
|
||||
session = sessions[session_id]
|
||||
session.characters[character.id] = character
|
||||
|
||||
# Notify storyteller
|
||||
storyteller_key = f"{session_id}_storyteller"
|
||||
if storyteller_key in manager.active_connections:
|
||||
await manager.send_to_client(storyteller_key, {
|
||||
"type": "character_joined",
|
||||
"character": {
|
||||
"id": character.id,
|
||||
"name": character.name,
|
||||
"description": character.description,
|
||||
"llm_model": character.llm_model,
|
||||
"profile": character.profile.dict() if character.profile else None
|
||||
}
|
||||
})
|
||||
|
||||
return character
|
||||
except Exception as e:
|
||||
raise HTTPException(status_code=400, detail=f"Invalid character data: {str(e)}")
|
||||
|
||||
# Get profile options
|
||||
@app.get("/profile/options")
|
||||
async def get_profile_options():
|
||||
"""Get available profile options for character creation"""
|
||||
return {
|
||||
"genders": ["Male", "Female", "Non-binary", "Custom"],
|
||||
"races": list(RACE_PROMPTS.keys()),
|
||||
"classes": list(CLASS_PROMPTS.keys()),
|
||||
"personality_types": list(PERSONALITY_PROMPTS.keys()),
|
||||
"race_descriptions": {
|
||||
"Human": "Versatile and adaptable",
|
||||
"Elf": "Graceful, wise, with keen senses",
|
||||
"Dwarf": "Stout, loyal, master craftsmen",
|
||||
"Orc": "Powerful, direct, honorable",
|
||||
"Halfling": "Small, brave, lucky"
|
||||
},
|
||||
"class_descriptions": {
|
||||
"Warrior": "Physical combat and tactics",
|
||||
"Wizard": "Arcane magic and knowledge",
|
||||
"Cleric": "Divine power and healing",
|
||||
"Archer": "Ranged combat and precision",
|
||||
"Rogue": "Stealth, cunning, and skills"
|
||||
},
|
||||
"personality_descriptions": {
|
||||
"Friendly": "Optimistic and cooperative",
|
||||
"Serious": "Focused and pragmatic",
|
||||
"Doubtful": "Cautious and analytical",
|
||||
"Measured": "Balanced and thoughtful"
|
||||
}
|
||||
}
|
||||
|
||||
# WebSocket endpoint for character interactions (character view)
|
||||
@app.websocket("/ws/character/{session_id}/{character_id}")
|
||||
async def character_websocket(websocket: WebSocket, session_id: str, character_id: str):
|
||||
@@ -338,11 +524,15 @@ async def generate_suggestion(session_id: str, character_id: str, context: str =
|
||||
|
||||
character = session.characters[character_id]
|
||||
|
||||
# Prepare context for AI suggestion
|
||||
# Prepare context for AI suggestion using character profile
|
||||
system_prompt = build_character_system_prompt(character)
|
||||
if session.current_scene:
|
||||
system_prompt += f" Current scene: {session.current_scene}"
|
||||
|
||||
messages = [
|
||||
{
|
||||
"role": "system",
|
||||
"content": f"You are {character.name} in an RPG. Respond in character. Character description: {character.description}. Personality: {character.personality}. Current scene: {session.current_scene}"
|
||||
"content": system_prompt
|
||||
}
|
||||
]
|
||||
|
||||
|
||||
Reference in New Issue
Block a user