mirror of
https://github.com/Kelsidavis/WoWee.git
synced 2026-03-22 23:30:14 +00:00
Clean repository artifacts and refresh project documentation
This commit is contained in:
parent
c20d5441d0
commit
274a88097f
9 changed files with 107 additions and 1683 deletions
|
|
@ -1,175 +1,135 @@
|
|||
# Build Instructions - Remove Single-Player Branch
|
||||
# Build Instructions
|
||||
|
||||
## Current Status
|
||||
This project builds as a native C++ client for WoW 3.3.5a in online mode.
|
||||
|
||||
✅ **Code Ready**: All single-player code removed, all compilation errors fixed
|
||||
✅ **Branch**: `remove-single-player`
|
||||
✅ **Commits**: 4 commits ahead of master
|
||||
✅ **Quality**: 450/450 braces balanced, 0 SP references, 0 SQLite references
|
||||
## 1. Install Dependencies
|
||||
|
||||
## Quick Start
|
||||
|
||||
### Option 1: Automated (Recommended)
|
||||
### Ubuntu / Debian
|
||||
|
||||
```bash
|
||||
# Install dependencies (requires sudo)
|
||||
/tmp/install_deps.sh
|
||||
|
||||
# Build the project
|
||||
/tmp/build_wowee.sh
|
||||
```
|
||||
|
||||
### Option 2: Manual
|
||||
|
||||
```bash
|
||||
# Install dependencies
|
||||
sudo apt update
|
||||
sudo apt install -y \
|
||||
libsdl2-dev libglew-dev libglm-dev zlib1g-dev \
|
||||
libavformat-dev libavcodec-dev libswscale-dev libavutil-dev \
|
||||
build-essential pkg-config git
|
||||
cmake build-essential pkg-config git \
|
||||
libsdl2-dev libglew-dev libglm-dev \
|
||||
libssl-dev zlib1g-dev \
|
||||
libavformat-dev libavcodec-dev libswscale-dev libavutil-dev \
|
||||
libstorm-dev
|
||||
```
|
||||
|
||||
# Build StormLib (if not in repos)
|
||||
If `libstorm-dev` is unavailable in your distro repos, build StormLib from source:
|
||||
|
||||
```bash
|
||||
cd /tmp
|
||||
git clone https://github.com/ladislav-zezula/StormLib.git
|
||||
cd StormLib && mkdir build && cd build
|
||||
cmake .. && make -j$(nproc)
|
||||
sudo make install && sudo ldconfig
|
||||
|
||||
# Build Wowee
|
||||
cd /home/k/wowee/build
|
||||
cd StormLib
|
||||
mkdir build && cd build
|
||||
cmake ..
|
||||
make -j$(nproc)
|
||||
|
||||
# Run
|
||||
./bin/wowee
|
||||
```
|
||||
|
||||
## What Was Changed
|
||||
|
||||
### Removed (~1,400 lines)
|
||||
- SQLite3 database wrapper (~700 lines)
|
||||
- Single-player persistence (~500 lines)
|
||||
- SP method implementations (27 methods)
|
||||
- SP UI elements (buttons, settings)
|
||||
- SP conditional logic throughout codebase
|
||||
|
||||
### Fixed
|
||||
- Missing closing brace in `update()` function
|
||||
- Removed calls to deleted methods (`getItemTemplateName`, `notifyInventoryChanged`, etc.)
|
||||
- Restored NPC animation callbacks (needed for online mode)
|
||||
- Fixed header corruption
|
||||
|
||||
### Preserved (100%)
|
||||
- All online multiplayer features
|
||||
- Authentication (SRP6a)
|
||||
- Character system
|
||||
- Combat system
|
||||
- Inventory & equipment
|
||||
- Quest system
|
||||
- Loot system
|
||||
- Spell system
|
||||
- Chat system
|
||||
- All rendering features
|
||||
|
||||
## Expected Build Output
|
||||
|
||||
```
|
||||
[ 1%] Building CXX object CMakeFiles/wowee.dir/src/core/application.cpp.o
|
||||
[ 3%] Building CXX object CMakeFiles/wowee.dir/src/core/window.cpp.o
|
||||
...
|
||||
[ 95%] Building CXX object CMakeFiles/wowee.dir/src/ui/talent_screen.cpp.o
|
||||
[ 97%] Building CXX object CMakeFiles/wowee.dir/src/main.cpp.o
|
||||
[100%] Linking CXX executable bin/wowee
|
||||
[100%] Built target wowee
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### CMake can't find SDL2
|
||||
```bash
|
||||
sudo apt install libsdl2-dev
|
||||
```
|
||||
|
||||
### CMake can't find StormLib
|
||||
StormLib is not in standard Ubuntu repos. Build from source:
|
||||
```bash
|
||||
cd /tmp
|
||||
git clone https://github.com/ladislav-zezula/StormLib.git
|
||||
cd StormLib && mkdir build && cd build
|
||||
cmake .. && make -j$(nproc) && sudo make install
|
||||
make -j"$(nproc)"
|
||||
sudo make install
|
||||
sudo ldconfig
|
||||
```
|
||||
|
||||
### Compilation errors
|
||||
If you see compilation errors, ensure you're on the correct branch:
|
||||
### Fedora
|
||||
|
||||
```bash
|
||||
git branch --show-current # Should show: remove-single-player
|
||||
git status # Should show: nothing to commit, working tree clean
|
||||
sudo dnf install -y \
|
||||
cmake gcc-c++ make pkg-config git \
|
||||
SDL2-devel glew-devel glm-devel \
|
||||
openssl-devel zlib-devel \
|
||||
ffmpeg-devel \
|
||||
StormLib-devel
|
||||
```
|
||||
|
||||
### Missing WoW Data
|
||||
The client requires WoW 3.3.5a data files in `Data/` directory:
|
||||
```
|
||||
wowee/
|
||||
└── Data/
|
||||
├── common.MPQ
|
||||
├── expansion.MPQ
|
||||
├── lichking.MPQ
|
||||
├── patch.MPQ
|
||||
└── enUS/
|
||||
```
|
||||
### Arch
|
||||
|
||||
Or set environment variable:
|
||||
```bash
|
||||
export WOW_DATA_PATH=/path/to/your/wow/Data
|
||||
sudo pacman -S --needed \
|
||||
cmake base-devel pkgconf git \
|
||||
sdl2 glew glm openssl zlib ffmpeg stormlib
|
||||
```
|
||||
|
||||
## Testing Checklist
|
||||
## 2. Clone + Prepare
|
||||
|
||||
After successful build:
|
||||
```bash
|
||||
git clone git@github.com:Kelsidavis/wowee.git
|
||||
cd wowee
|
||||
git clone https://github.com/ocornut/imgui.git extern/imgui
|
||||
```
|
||||
|
||||
- [ ] Application launches without crashes
|
||||
- [ ] Can connect to auth server
|
||||
- [ ] Can view realm list
|
||||
- [ ] Can view/create/delete characters
|
||||
- [ ] Can enter world
|
||||
- [ ] Movement works (WASD)
|
||||
- [ ] Combat works (auto-attack, spells)
|
||||
- [ ] Inventory system functional
|
||||
- [ ] Quest markers appear
|
||||
- [ ] Loot window opens
|
||||
- [ ] Chat works
|
||||
## 3. Configure + Build
|
||||
|
||||
## Performance
|
||||
```bash
|
||||
cmake -S . -B build -DCMAKE_BUILD_TYPE=Release
|
||||
cmake --build build -j"$(nproc)"
|
||||
```
|
||||
|
||||
Expected performance:
|
||||
- **FPS**: 60 (vsync)
|
||||
- **Triangles/frame**: ~50k
|
||||
- **Draw calls**: ~30
|
||||
- **GPU Usage**: <10%
|
||||
Binary output:
|
||||
|
||||
## Next Steps
|
||||
```text
|
||||
build/bin/wowee
|
||||
```
|
||||
|
||||
1. Install dependencies: `/tmp/install_deps.sh`
|
||||
2. Build project: `/tmp/build_wowee.sh`
|
||||
3. Test online features
|
||||
4. Merge to master when satisfied:
|
||||
```bash
|
||||
git checkout master
|
||||
git merge remove-single-player
|
||||
git push
|
||||
```
|
||||
## 4. Provide WoW 3.3.5a Data
|
||||
|
||||
## Support
|
||||
Supply your own legally obtained data files in either:
|
||||
|
||||
If you encounter issues:
|
||||
1. Check branch: `git branch --show-current`
|
||||
2. Check status: `git status`
|
||||
3. Check commits: `git log --oneline -5`
|
||||
4. Verify balance: `grep -c "{" src/game/game_handler.cpp` should equal `grep -c "}" src/game/game_handler.cpp`
|
||||
1. `./Data/`
|
||||
2. Path pointed to by `WOW_DATA_PATH`
|
||||
|
||||
---
|
||||
Example:
|
||||
|
||||
Last updated: 2026-02-07
|
||||
Branch: remove-single-player (4 commits ahead of master)
|
||||
Status: Ready to build
|
||||
```text
|
||||
Data/
|
||||
common.MPQ
|
||||
common-2.MPQ
|
||||
expansion.MPQ
|
||||
lichking.MPQ
|
||||
patch.MPQ
|
||||
patch-2.MPQ
|
||||
patch-3.MPQ
|
||||
enUS/
|
||||
```
|
||||
|
||||
## 5. Run
|
||||
|
||||
```bash
|
||||
./build/bin/wowee
|
||||
```
|
||||
|
||||
## 6. Local AzerothCore (Optional)
|
||||
|
||||
If you are using a local AzerothCore Docker stack, start it first and then connect from the client realm screen.
|
||||
|
||||
See:
|
||||
|
||||
- `docs/server-setup.md`
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### `StormLib` not found
|
||||
|
||||
Install distro package or build from source (section 1).
|
||||
|
||||
### `ImGui` missing
|
||||
|
||||
Ensure `extern/imgui` exists:
|
||||
|
||||
```bash
|
||||
git clone https://github.com/ocornut/imgui.git extern/imgui
|
||||
```
|
||||
|
||||
### MPQ/Data not found at runtime
|
||||
|
||||
Place data under `./Data` or set:
|
||||
|
||||
```bash
|
||||
export WOW_DATA_PATH=/path/to/WoW/Data
|
||||
```
|
||||
|
||||
### Clean rebuild
|
||||
|
||||
```bash
|
||||
rm -rf build
|
||||
cmake -S . -B build -DCMAKE_BUILD_TYPE=Release
|
||||
cmake --build build -j"$(nproc)"
|
||||
```
|
||||
|
|
|
|||
209
CHANGELOG.md
209
CHANGELOG.md
|
|
@ -1,209 +0,0 @@
|
|||
# Changelog
|
||||
|
||||
All notable changes to the Wowee project are documented here.
|
||||
|
||||
## Recent Development (2024-2026)
|
||||
|
||||
### Architecture Changes
|
||||
- **Removed single-player mode**: Removed offline/single-player functionality to focus exclusively on multiplayer. This includes removal of SQLite persistence, local combat simulation, and all single-player UI elements.
|
||||
|
||||
### Quest System
|
||||
- **Quest markers**: Added ! (quest available) and ? (quest complete) markers above NPCs
|
||||
- **Minimap integration**: Quest markers now appear on minimap for easy navigation
|
||||
- **Quest log**: Full quest log UI with objectives, progress tracking, and rewards
|
||||
- **Quest details dialog**: Rich quest details window with description and objectives
|
||||
- **Quest turn-in flow**: Complete quest workflow from accept to turn-in with reward selection
|
||||
- **Quest giver status**: Automatic CMSG_QUESTGIVER_STATUS_QUERY when NPCs spawn
|
||||
- **Status re-query**: Re-query quest status after accepting or completing quests
|
||||
|
||||
### Spellbook & Action Bar
|
||||
- **Class specialty tabs**: Spellbook organized by SkillLine specialties using SkillLine.dbc and SkillLineAbility.dbc
|
||||
- **General tab**: Separate tab for universal spells
|
||||
- **Spell icons**: Loaded from SpellIcon.dbc with proper rendering
|
||||
- **Drag-drop system**: Drag spells from spellbook to action bar slots
|
||||
- **Click-to-cast**: Click action bar slots to cast spells
|
||||
- **Spell targeting**: Proper spell targeting implementation
|
||||
- **Error messages**: Clear error messages for spell cast failures
|
||||
- **Cooldown tracking**: Visual cooldown indicators on action bar
|
||||
- **Keybindings**: 1-9, 0, -, = for quick action bar access
|
||||
- **Window behavior**: Fixed spellbook window dragging and escape-from-bounds issues
|
||||
|
||||
### Inventory & Equipment
|
||||
- **Equipment slots**: 23 slots (head, shoulders, chest, legs, feet, wrist, hands, waist, back, mainhand, offhand, ranged, etc.)
|
||||
- **Backpack**: 16-slot backpack storage
|
||||
- **Item icons**: Loaded from ItemDisplayInfo.dbc
|
||||
- **Drag-drop**: Drag items between inventory, equipment, and action bar
|
||||
- **Auto-equip**: Automatic equipment slot detection and equipping
|
||||
- **Item tooltips**: Rich tooltips with item stats and information
|
||||
- **Online sync**: Proper GUID resolution and inventory enrichment
|
||||
- **Slot mapping**: Fixed online equipment slot mapping and backpack offsets
|
||||
|
||||
### Vendor System
|
||||
- **Buy items**: Purchase items from vendors with gold
|
||||
- **Sell items**: Sell items back to vendors (online and offline)
|
||||
- **Gold tracking**: Proper coinage field (PLAYER_FIELD_COINAGE at index 1170)
|
||||
- **Inventory errors**: Handle sell/inventory errors gracefully
|
||||
- **UI improvements**: Clean vendor interface with item lists
|
||||
|
||||
### Loot System
|
||||
- **Loot window**: Visual loot window with item icons
|
||||
- **Gold looting**: CMSG_LOOT_MONEY packet for online gold pickup
|
||||
- **Item pickup**: Automatic item transfer to inventory
|
||||
- **Corpse looting**: Loot from defeated enemies
|
||||
|
||||
### Combat System
|
||||
- **Auto-attack**: Automatic attack on targeted enemies
|
||||
- **Spell casting**: Full spell casting with resource costs (mana/rage/energy)
|
||||
- **Attack animations**: Proper NPC and player attack animations
|
||||
- **Damage calculation**: Server-side damage processing
|
||||
- **Death handling**: Player death, corpse creation, resurrection
|
||||
- **Faction hostility**: Faction.dbc-based hostility using base reputation
|
||||
- **Race-aware factions**: Proper faction checking for all player races
|
||||
- **Neutral-flagged hostile**: Support for neutral-flagged hostile mobs (Monster faction group)
|
||||
- **Level-based coloring**: WoW-canonical mob level colors (gray, green, yellow, orange, red)
|
||||
|
||||
### Character System
|
||||
- **Character creation**: Full creation flow with race, class, gender, appearance
|
||||
- **Character screen**: 3D animated character preview
|
||||
- **Stats panel**: Display level, race, class, location on character screen
|
||||
- **Model preview**: 3D character model on creation and selection screens
|
||||
- **All races**: Support for all Alliance and Horde races
|
||||
- **Texture support**: Race-aware skin, hair, and feature textures
|
||||
- **Auto-select**: Auto-select single realm or single character
|
||||
- **Logout cleanup**: Clear character state on logout to prevent stale models
|
||||
|
||||
### M2 Model Rendering
|
||||
- **Particle emitters**: Enabled M2 particle emitters with WotLK struct parsing
|
||||
- **FBlock format**: Correct FBlock format and struct size for particle data
|
||||
- **Safety caps**: Overflow guards and safety caps for emitter parameters
|
||||
- **Glow rendering**: Billboarded light sprites for M2 glow batches
|
||||
- **Blend modes**: Skip additive/mod blend batches for correct rendering
|
||||
- **Unlit rendering**: Unlit shader path for glow and additive batches
|
||||
- **Lantern glow**: Fixed lantern and torch glow rendering
|
||||
|
||||
### NPCs & Gossip
|
||||
- **Gossip system**: NPC dialogue with options
|
||||
- **Gossip packets**: CMSG_GOSSIP_SELECT_OPTION with proper opcode
|
||||
- **Duplicate prevention**: Clear gossip options before re-parsing
|
||||
- **Reopen guard**: Prevent gossip window conflicts
|
||||
- **Combat animations**: NPCs play combat animations during attacks
|
||||
- **Creature spawning**: Camera intro animation on all creature spawns
|
||||
- **Display lookups**: Pre-load CreatureDisplayInfo DBC at startup
|
||||
|
||||
### Movement & Navigation
|
||||
- **WASD movement**: Smooth WASD character movement
|
||||
- **Camera orbit**: Mouse-based camera orbit around character
|
||||
- **Spline movement**: Follow server-side spline paths
|
||||
- **Fall time**: Correct movement packet format (unconditional fallTime write)
|
||||
- **Position updates**: Smooth position interpolation
|
||||
- **Respawn handling**: Fixed respawned corpse movement
|
||||
|
||||
### Terrain & World
|
||||
- **Async loading**: Asynchronous terrain streaming to prevent hang
|
||||
- **Streaming loop**: Fixed terrain streaming loop for continuous loading
|
||||
- **Multi-tile support**: Load multiple ADT tiles simultaneously
|
||||
- **Auto-load**: Load terrain as player moves through world
|
||||
- **Height maps**: Proper height calculation for player positioning
|
||||
|
||||
### UI Improvements
|
||||
- **Loading screen**: Loading screen with progress bar during world entry
|
||||
- **Resize handling**: Proper resize handling during loading
|
||||
- **Progress tracking**: Visual progress percentage
|
||||
- **UI opacity**: Slider to adjust UI opacity in settings
|
||||
- **ImGui frame conflict**: Fixed ImGui frame management issues
|
||||
- **Popup positioning**: Fixed popup window positioning
|
||||
- **ID conflicts**: Resolved ImGui widget ID conflicts
|
||||
- **Both-button clicks**: Suppress simultaneous left+right mouse clicks
|
||||
- **Player name display**: Fixed player name rendering in UI
|
||||
- **Target frame**: Display targeted entity name, level, health
|
||||
|
||||
### Chat System
|
||||
- **Chat window**: Scrollable chat window with message history
|
||||
- **Message formatting**: Proper chat message formatting with colors
|
||||
- **Chat commands**: /say, /yell, /whisper support
|
||||
- **Chat input**: Press Enter to open chat, type and send
|
||||
|
||||
### Minimap
|
||||
- **Quest markers**: Show quest givers and turn-in NPCs
|
||||
- **Player position**: Display player position and direction
|
||||
- **Zoom**: Minimap zoom levels
|
||||
|
||||
### Rendering Improvements
|
||||
- **WMO distance cull**: Increased WMO group distance cull from 80 to 160 units
|
||||
- **Hair textures**: Fixed hair texture loading and rendering
|
||||
- **Skin textures**: Proper skin color and texture application
|
||||
- **Action bar icons**: Spell and item icons on action bar
|
||||
- **Targeting visuals**: Visual targeting indicators
|
||||
|
||||
### Network & Protocol
|
||||
- **Opcode fixes**: Corrected loot and gossip opcodes for 3.3.5a
|
||||
- **Movement packets**: Fixed MOVE_* packet format
|
||||
- **Quest opcodes**: Added quest-related opcodes
|
||||
- **Item queries**: Proper CMSG_ITEM_QUERY_SINGLE parsing
|
||||
- **Sell item packets**: CMSG_SELL_ITEM with correct uint32 count
|
||||
|
||||
### Performance
|
||||
- **Frame stalls**: Eliminated stalls from terrain loading (async)
|
||||
- **Startup optimization**: Load DBC lookups at startup
|
||||
- **Log truncation**: Truncate log file on start to prevent bloat
|
||||
- **Memory efficiency**: Proper cleanup and resource management
|
||||
|
||||
### Bug Fixes
|
||||
- **Vendor bugs**: Fixed vendor gold calculation and item display
|
||||
- **Loot bugs**: Fixed loot window showing incorrect items
|
||||
- **Hair bugs**: Fixed hair texture selection and rendering
|
||||
- **Critter hostility**: Fixed neutral critters not being attackable
|
||||
- **Faction bugs**: Fixed Monster faction group bit (use 8 not 4)
|
||||
- **XP calculation**: Proper level-based XP from mob kills
|
||||
- **Respawn bugs**: Fixed corpse movement after respawn
|
||||
- **Camera bugs**: Fixed camera orbit and deselect behavior
|
||||
- **Spell targeting**: Fixed spell targeting for ranged abilities
|
||||
- **Action bar**: Fixed drag-drop and right-click removal
|
||||
- **Character screen**: Various character screen display bugs
|
||||
- **Stale models**: Prevent stale player model across logins
|
||||
|
||||
### Single-Player Mode
|
||||
- **Offline play**: Full offline mode without server
|
||||
- **Local persistence**: SQLite-based character and settings storage
|
||||
- **Simulated combat**: Local XP and damage calculation
|
||||
- **Settings sync**: Save and load settings locally
|
||||
|
||||
## Future Roadmap
|
||||
|
||||
### Planned Features
|
||||
- Talent system implementation
|
||||
- Guild system
|
||||
- Auction house
|
||||
- Mail system
|
||||
- Crafting and professions
|
||||
- Achievements
|
||||
- Dungeon finder
|
||||
- Battlegrounds and PvP
|
||||
- Mount system
|
||||
- Pet system
|
||||
|
||||
### Rendering Improvements
|
||||
- LOD (Level of Detail) system
|
||||
- Improved shadow quality
|
||||
- SSAO (Screen Space Ambient Occlusion)
|
||||
- Better water caustics
|
||||
- Improved particle effects
|
||||
|
||||
### Performance Optimizations
|
||||
- Multi-threaded asset loading
|
||||
- Occlusion culling improvements
|
||||
- Texture compression
|
||||
- Model instancing
|
||||
- Shader optimizations
|
||||
|
||||
### Quality of Life
|
||||
- Keybinding customization UI
|
||||
- Graphics settings menu
|
||||
- Audio volume controls
|
||||
- Addon support
|
||||
- Macros
|
||||
- UI customization
|
||||
|
||||
---
|
||||
|
||||
See [GitHub commit history](https://github.com/yourname/wowee/commits) for detailed commit messages and technical changes.
|
||||
628
FEATURES.md
628
FEATURES.md
|
|
@ -1,628 +0,0 @@
|
|||
# Features Overview
|
||||
|
||||
A comprehensive overview of all implemented features in Wowee, the native C++ World of Warcraft 3.3.5a client.
|
||||
|
||||
## Table of Contents
|
||||
- [Rendering Features](#rendering-features)
|
||||
- [Gameplay Features](#gameplay-features)
|
||||
- [UI Features](#ui-features)
|
||||
- [Network & Authentication](#network--authentication)
|
||||
- [Asset Pipeline](#asset-pipeline)
|
||||
- [Audio Features](#audio-features)
|
||||
- [Developer Tools](#developer-tools)
|
||||
|
||||
---
|
||||
|
||||
## Rendering Features
|
||||
|
||||
### Terrain Rendering
|
||||
- ✅ **Multi-tile streaming**: Load and render multiple ADT terrain tiles
|
||||
- ✅ **Async loading**: Non-blocking terrain chunk loading (prevents frame stalls)
|
||||
- ✅ **Height maps**: 9x9 outer + 8x8 inner vertex grids per chunk
|
||||
- ✅ **Texture splatting**: Up to 4 texture layers per chunk with alpha blending
|
||||
- ✅ **Frustum culling**: Only render visible terrain chunks
|
||||
- ✅ **Terrain holes**: Support for gaps in terrain geometry
|
||||
|
||||
### Water & Liquids
|
||||
- ✅ **Animated water**: Vertex animation with wave motion
|
||||
- ✅ **Reflections**: Sky and environment reflections on water surface
|
||||
- ✅ **Refractions**: Underwater view distortion
|
||||
- ✅ **Fresnel effect**: View-angle dependent reflection/refraction mixing
|
||||
- ✅ **Multiple liquid types**: Water, lava, slime support
|
||||
- ✅ **Liquid height**: Variable water levels per chunk
|
||||
|
||||
### Sky & Atmosphere
|
||||
- ✅ **Dynamic day/night cycle**: Smooth time-of-day transitions
|
||||
- ✅ **Sun and moon**: Orbital movement with proper positioning
|
||||
- ✅ **Moon phases**: 8 realistic lunar phases with elliptical terminator
|
||||
- ✅ **Star field**: 1000+ procedurally placed stars (visible at night)
|
||||
- ✅ **Gradient sky**: Time-dependent sky color gradients
|
||||
- ✅ **Manual time control**: F9 to pause, +/- to adjust time
|
||||
|
||||
### Weather & Particles
|
||||
- ✅ **Rain system**: 2000 particle rain with gravity and wind
|
||||
- ✅ **Snow system**: 2000 particle snow with drift and accumulation
|
||||
- ✅ **Camera-relative particles**: Particles follow camera for consistent coverage
|
||||
- ✅ **Weather cycling**: W key to cycle None/Rain/Snow
|
||||
- ✅ **M2 particle emitters**: WotLK-compatible particle emitters on models
|
||||
|
||||
### Characters & Models
|
||||
- ✅ **M2 model loading**: Character, creature, and prop models
|
||||
- ✅ **Skeletal animation**: Up to 256 bones per model with GPU skinning
|
||||
- ✅ **Animation sequences**: Idle, walk, run, attack, death, emote, etc.
|
||||
- ✅ **Multiple animations**: Smooth animation blending
|
||||
- ✅ **Geosets**: Show/hide body parts (e.g., helmets, cloaks)
|
||||
- ✅ **Attachment points**: Weapons, shields, helmets properly attached
|
||||
- ✅ **Race-aware textures**: Correct skin, hair, and face textures for all races
|
||||
- ✅ **All races supported**: Human, Dwarf, Night Elf, Gnome, Draenei, Orc, Undead, Tauren, Troll, Blood Elf
|
||||
|
||||
### Buildings & World Objects
|
||||
- ✅ **WMO rendering**: World Map Object (building) rendering
|
||||
- ✅ **Multi-material batches**: Multiple textures per building
|
||||
- ✅ **Portal system**: Visibility culling using portals
|
||||
- ✅ **Doodad placement**: Decorative objects within buildings
|
||||
- ✅ **Distance culling**: WMO groups culled beyond 160 units
|
||||
- ✅ **Frustum culling**: Only render visible building groups
|
||||
|
||||
### Visual Effects
|
||||
- ✅ **Lens flare**: Chromatic aberration sun lens flare
|
||||
- ✅ **Volumetric clouds**: FBM noise-based cloud generation
|
||||
- ✅ **Glow effects**: Billboarded light sprites for lanterns, torches
|
||||
- ✅ **Blend modes**: Proper alpha, additive, and modulate blending
|
||||
- ✅ **Unlit rendering**: Separate shader path for emissive materials
|
||||
|
||||
### Post-Processing
|
||||
- ✅ **HDR rendering**: High dynamic range rendering pipeline
|
||||
- ✅ **Tonemapping**: Exposure adjustment and color grading
|
||||
- ✅ **Shadow mapping**: 2048x2048 shadow maps
|
||||
- ✅ **MSAA support**: Multi-sample anti-aliasing
|
||||
|
||||
### Camera
|
||||
- ✅ **Free-fly camera**: WASD movement with mouse look
|
||||
- ✅ **Camera orbit**: Orbit around character in online mode
|
||||
- ✅ **Sprint**: Shift key for faster camera movement
|
||||
- ✅ **Smooth movement**: Interpolated camera transitions
|
||||
- ✅ **Intro animations**: Camera swoops on creature spawns
|
||||
|
||||
---
|
||||
|
||||
## Gameplay Features
|
||||
|
||||
### Authentication & Login
|
||||
- ✅ **SRP6a authentication**: Full cryptographic authentication
|
||||
- ✅ **Username/password**: Standard login credentials
|
||||
- ✅ **Server selection**: Configure auth server address
|
||||
- ✅ **Session keys**: 40-byte session key generation
|
||||
- ✅ **RC4 encryption**: Header encryption after authentication
|
||||
- ✅ **Auto-connect**: Reconnect on disconnect
|
||||
|
||||
### Realm & Character Selection
|
||||
- ✅ **Realm list**: Display available realms from auth server
|
||||
- ✅ **Realm info**: Population, type (PvP/PvE/RP), online status
|
||||
- ✅ **Auto-select**: Auto-select when only one realm available
|
||||
- ✅ **Character list**: Display all characters on selected realm
|
||||
- ✅ **Character preview**: 3D animated character preview
|
||||
- ✅ **Character stats**: Level, race, class, location display
|
||||
- ✅ **Auto-select character**: Auto-select when only one character exists
|
||||
|
||||
### Character Creation
|
||||
- ✅ **Race selection**: All 10 playable races (Alliance and Horde)
|
||||
- ✅ **Class selection**: Classes filtered by race compatibility
|
||||
- ✅ **Gender selection**: Male and female options
|
||||
- ✅ **Appearance customization**: Face, skin color, hair style, hair color, facial features
|
||||
- ✅ **Name validation**: Character name input and validation
|
||||
- ✅ **3D preview**: Real-time 3D character preview during creation
|
||||
- ✅ **Character deletion**: Delete existing characters
|
||||
|
||||
### Movement & Navigation
|
||||
- ✅ **WASD movement**: Smooth character movement
|
||||
- ✅ **Mouse steering**: Camera-relative movement direction
|
||||
- ✅ **Sprint**: Shift key for faster movement
|
||||
- ✅ **Server sync**: Position synchronized with world server
|
||||
- ✅ **Spline movement**: Follow server-dictated movement paths
|
||||
- ✅ **Fall time**: Proper gravity and fall damage calculation
|
||||
- ✅ **Collision**: Terrain height-based positioning
|
||||
|
||||
### Combat System
|
||||
- ✅ **Targeting**: Left-click or Tab to target enemies
|
||||
- ✅ **Auto-attack**: Automatic melee attacks on targeted enemy
|
||||
- ✅ **Spell casting**: Cast spells from spellbook or action bar
|
||||
- ✅ **Spell targeting**: Click-to-target and self-cast support
|
||||
- ✅ **Cooldowns**: Visual cooldown indicators on action bar
|
||||
- ✅ **Resource costs**: Mana, rage, energy consumption
|
||||
- ✅ **Damage calculation**: Server-side damage processing
|
||||
- ✅ **Attack animations**: Proper melee and spell cast animations
|
||||
- ✅ **Death handling**: Player death, corpse, resurrection
|
||||
- ✅ **NPC combat**: NPCs attack and animate properly
|
||||
- ✅ **Faction hostility**: Faction.dbc-based friend/foe detection
|
||||
- ✅ **Level-based difficulty**: Color-coded enemy levels (gray/green/yellow/orange/red)
|
||||
|
||||
### Spells & Abilities
|
||||
- ✅ **Spellbook**: Complete spellbook UI
|
||||
- ✅ **Class specialties**: Tabs organized by SkillLine (e.g., Fire, Frost, Arcane for Mage)
|
||||
- ✅ **General tab**: Universal spells available to all classes
|
||||
- ✅ **Spell icons**: Loaded from SpellIcon.dbc
|
||||
- ✅ **Spell tooltips**: Name, rank, cost, range, cooldown, description
|
||||
- ✅ **Drag-drop**: Drag spells to action bar
|
||||
- ✅ **Known spells**: Track learned spells per character
|
||||
- ✅ **Spell ranks**: Multiple ranks per spell
|
||||
|
||||
### Action Bar
|
||||
- ✅ **12 slots**: Main action bar with 12 ability slots
|
||||
- ✅ **Keybindings**: 1-9, 0, -, = for quick access
|
||||
- ✅ **Spell icons**: Visual spell icons with cooldown overlay
|
||||
- ✅ **Item icons**: Visual item icons for usable items
|
||||
- ✅ **Drag-drop**: Drag spells from spellbook or items from inventory
|
||||
- ✅ **Click-to-cast**: Left-click to use ability
|
||||
- ✅ **Drag-to-remove**: Drag to ground to remove from action bar
|
||||
- ✅ **Cooldown display**: Visual cooldown timer
|
||||
- ✅ **Hotkey labels**: Show keybinding on each slot
|
||||
|
||||
### Inventory & Equipment
|
||||
- ✅ **23 equipment slots**: Head, shoulders, chest, legs, feet, wrist, hands, waist, back, mainhand, offhand, ranged, ammo, tabard, shirt, trinkets, rings, neck
|
||||
- ✅ **16 backpack slots**: Main backpack storage
|
||||
- ✅ **Item icons**: Rich item icons from ItemDisplayInfo.dbc
|
||||
- ✅ **Item tooltips**: Stats, durability, item level, required level
|
||||
- ✅ **Drag-drop**: Drag items to equip, unequip, or action bar
|
||||
- ✅ **Auto-equip**: Double-click or drag to auto-equip to correct slot
|
||||
- ✅ **Gold display**: Current gold/silver/copper
|
||||
- ✅ **Item stats**: Armor, damage, stats, enchantments
|
||||
- ✅ **Durability**: Equipment durability tracking
|
||||
|
||||
### Quest System
|
||||
- ✅ **Quest markers**: ! (available) and ? (complete) above NPCs
|
||||
- ✅ **Minimap markers**: Quest markers on minimap
|
||||
- ✅ **Quest details**: Rich quest description and objectives
|
||||
- ✅ **Quest log**: Track up to 25 active quests
|
||||
- ✅ **Objective tracking**: Progress on kill/collect objectives
|
||||
- ✅ **Quest rewards**: Choose reward items on completion
|
||||
- ✅ **Quest turn-in**: Complete quest workflow
|
||||
- ✅ **Quest levels**: Color-coded quest difficulty
|
||||
- ✅ **Abandon quests**: Drop unwanted quests
|
||||
- ✅ **Quest giver status**: Dynamic ! and ? based on quest state
|
||||
|
||||
### Vendor System
|
||||
- ✅ **Buy items**: Purchase items with gold
|
||||
- ✅ **Sell items**: Sell items from inventory
|
||||
- ✅ **Vendor inventory**: Display vendor's available items
|
||||
- ✅ **Price display**: Gold/silver/copper prices
|
||||
- ✅ **Gold validation**: Prevent buying without enough gold
|
||||
- ✅ **Inventory space check**: Verify space before buying
|
||||
- ✅ **Multi-buy**: Purchase multiple quantities
|
||||
|
||||
### Loot System
|
||||
- ✅ **Loot window**: Visual loot interface
|
||||
- ✅ **Loot corpses**: Loot from defeated enemies
|
||||
- ✅ **Gold looting**: Pick up gold from corpses
|
||||
- ✅ **Item looting**: Add looted items to inventory
|
||||
- ✅ **Loot all**: Take all items and gold
|
||||
- ✅ **Auto-loot**: Shift-click for instant loot (TODO)
|
||||
|
||||
### NPC Interaction
|
||||
- ✅ **Gossip system**: Talk to NPCs with dialogue options
|
||||
- ✅ **Gossip options**: Multiple choice dialogues
|
||||
- ✅ **Quest givers**: NPCs offer quests
|
||||
- ✅ **Vendors**: NPCs sell and buy items
|
||||
- ✅ **Trainers**: NPCs offer training (placeholder)
|
||||
- ✅ **Flight masters**: Flight points (TODO)
|
||||
|
||||
### Social Features
|
||||
- ✅ **Chat system**: Send and receive chat messages
|
||||
- ✅ **Chat channels**: SAY, YELL, WHISPER, GUILD (TODO)
|
||||
- ✅ **Chat formatting**: Color-coded messages by type
|
||||
- ✅ **Chat history**: Scrollable message history
|
||||
- ✅ **Party system**: Group invites and party list
|
||||
- ✅ **Friend list**: (TODO)
|
||||
- ✅ **Guild system**: (TODO)
|
||||
|
||||
### Character Progression
|
||||
- ✅ **Experience points**: Gain XP from kills and quests
|
||||
- ✅ **Leveling**: Level up with stat increases
|
||||
- ✅ **Level-based XP**: Appropriate XP from mob kills
|
||||
- ✅ **Stats tracking**: Health, mana, strength, agility, etc.
|
||||
- ✅ **Talent points**: (TODO - placeholder screen exists)
|
||||
- ✅ **Talent trees**: (TODO)
|
||||
|
||||
---
|
||||
|
||||
## UI Features
|
||||
|
||||
### Authentication Screen
|
||||
- ✅ Username input field
|
||||
- ✅ Password input field (masked)
|
||||
- ✅ Server address input
|
||||
- ✅ Login button
|
||||
- ✅ Connection status display
|
||||
- ✅ Error message display
|
||||
|
||||
### Realm Selection Screen
|
||||
- ✅ Realm list with names
|
||||
- ✅ Realm type indicators (PvP/PvE/RP)
|
||||
- ✅ Population display (Low/Medium/High/Full)
|
||||
- ✅ Online/offline status
|
||||
- ✅ Select button
|
||||
- ✅ Back to login button
|
||||
|
||||
### Character Selection Screen
|
||||
- ✅ Character list with names and levels
|
||||
- ✅ 3D animated character preview
|
||||
- ✅ Race, class, level display
|
||||
- ✅ Location display
|
||||
- ✅ Create Character button
|
||||
- ✅ Delete Character button
|
||||
- ✅ Enter World button
|
||||
- ✅ Back to realms button
|
||||
|
||||
### Character Creation Screen
|
||||
- ✅ Race selection buttons (all 10 races)
|
||||
- ✅ Class selection buttons (filtered by race)
|
||||
- ✅ Gender selection (male/female)
|
||||
- ✅ Face selection
|
||||
- ✅ Skin color selection
|
||||
- ✅ Hair style selection
|
||||
- ✅ Hair color selection
|
||||
- ✅ Facial features selection
|
||||
- ✅ Character name input
|
||||
- ✅ 3D character preview (updates in real-time)
|
||||
- ✅ Create button
|
||||
- ✅ Back button
|
||||
|
||||
### In-Game HUD
|
||||
- ✅ Player health bar
|
||||
- ✅ Player mana/rage/energy bar
|
||||
- ✅ Player level and name
|
||||
- ✅ Target frame (health, level, name)
|
||||
- ✅ Target hostility coloring (red=hostile, green=friendly, yellow=neutral)
|
||||
- ✅ Experience bar
|
||||
- ✅ Action bar (12 slots with icons and keybindings)
|
||||
- ✅ Minimap
|
||||
- ✅ Chat window
|
||||
- ✅ Gold display
|
||||
- ✅ Coordinates display (debug)
|
||||
|
||||
### Inventory Window
|
||||
- ✅ Paper doll (equipment visualization)
|
||||
- ✅ 23 equipment slots
|
||||
- ✅ Backpack grid (16 slots)
|
||||
- ✅ Item icons with tooltips
|
||||
- ✅ Gold display
|
||||
- ✅ Character stats panel
|
||||
- ✅ Close button
|
||||
|
||||
### Spellbook Window
|
||||
- ✅ Tabbed interface (class specs + General)
|
||||
- ✅ Spell list with icons
|
||||
- ✅ Spell names and ranks
|
||||
- ✅ Spell tooltips (cost, range, cooldown, description)
|
||||
- ✅ Drag-drop to action bar
|
||||
- ✅ Tab switching
|
||||
- ✅ Close button
|
||||
|
||||
### Quest Log Window
|
||||
- ✅ Quest list (up to 25 quests)
|
||||
- ✅ Quest objectives and progress
|
||||
- ✅ Quest description
|
||||
- ✅ Quest level and recommended party size
|
||||
- ✅ Abandon Quest button
|
||||
- ✅ Close button
|
||||
|
||||
### Quest Details Dialog
|
||||
- ✅ Quest title and level
|
||||
- ✅ Quest description text
|
||||
- ✅ Objectives list
|
||||
- ✅ Reward display (gold, items, XP)
|
||||
- ✅ Reward choice (select one of multiple rewards)
|
||||
- ✅ Accept button
|
||||
- ✅ Decline button
|
||||
|
||||
### Vendor Window
|
||||
- ✅ Vendor item list with icons
|
||||
- ✅ Item prices (gold/silver/copper)
|
||||
- ✅ Buy button per item
|
||||
- ✅ Sell tab (your items)
|
||||
- ✅ Buyback tab (TODO)
|
||||
- ✅ Close button
|
||||
|
||||
### Loot Window
|
||||
- ✅ Loot item list with icons
|
||||
- ✅ Item names and quantities
|
||||
- ✅ Gold display
|
||||
- ✅ Click to loot individual items
|
||||
- ✅ Auto-close when empty
|
||||
|
||||
### Gossip Window
|
||||
- ✅ NPC dialogue text
|
||||
- ✅ Gossip option buttons
|
||||
- ✅ Quest links
|
||||
- ✅ Vendor button
|
||||
- ✅ Trainer button
|
||||
- ✅ Close button
|
||||
|
||||
### Talent Window (Placeholder)
|
||||
- ✅ Talent tree visualization (TODO)
|
||||
- ✅ Talent point allocation (TODO)
|
||||
- ✅ Close button
|
||||
|
||||
### Settings Window
|
||||
- ✅ UI opacity slider
|
||||
- ✅ Graphics options (TODO)
|
||||
- ✅ Audio volume controls (TODO)
|
||||
- ✅ Keybinding customization (TODO)
|
||||
- ✅ Close button
|
||||
|
||||
### Loading Screen
|
||||
- ✅ Progress bar with percentage
|
||||
- ✅ Map name display (TODO)
|
||||
- ✅ Loading tips (TODO)
|
||||
- ✅ Background image (TODO)
|
||||
|
||||
### Performance HUD (F1)
|
||||
- ✅ FPS counter
|
||||
- ✅ Frame time (ms)
|
||||
- ✅ Draw calls
|
||||
- ✅ Triangle count
|
||||
- ✅ GPU usage %
|
||||
- ✅ Memory usage
|
||||
- ✅ Network stats (TODO)
|
||||
|
||||
### Minimap
|
||||
- ✅ Player position indicator
|
||||
- ✅ Player direction arrow
|
||||
- ✅ Quest markers (! and ?)
|
||||
- ✅ Zoom levels (TODO)
|
||||
- ✅ Zone name (TODO)
|
||||
|
||||
---
|
||||
|
||||
## Network & Authentication
|
||||
|
||||
### Connection
|
||||
- ✅ TCP socket abstraction
|
||||
- ✅ Non-blocking I/O
|
||||
- ✅ Packet framing (6-byte outgoing, 4-byte incoming headers)
|
||||
- ✅ Automatic reconnection
|
||||
- ✅ Connection status tracking
|
||||
|
||||
### Authentication (Port 3724)
|
||||
- ✅ SRP6a protocol implementation
|
||||
- ✅ LOGON_CHALLENGE packet
|
||||
- ✅ LOGON_PROOF packet
|
||||
- ✅ Session key generation (40 bytes)
|
||||
- ✅ SHA1 hashing (OpenSSL)
|
||||
- ✅ Big integer arithmetic
|
||||
- ✅ Salt and verifier calculation
|
||||
- ✅ Realm list retrieval
|
||||
|
||||
### World Server (Port 8085)
|
||||
- ✅ SMSG_AUTH_CHALLENGE / CMSG_AUTH_SESSION
|
||||
- ✅ RC4 header encryption
|
||||
- ✅ 100+ packet types implemented
|
||||
- ✅ Packet batching (multiple per frame)
|
||||
- ✅ Opcode handling for WoW 3.3.5a (build 12340)
|
||||
|
||||
### Implemented Packets (Partial List)
|
||||
- ✅ Character enumeration (SMSG_CHAR_ENUM)
|
||||
- ✅ Character creation (CMSG_CHAR_CREATE)
|
||||
- ✅ Character deletion (CMSG_CHAR_DELETE)
|
||||
- ✅ Player login (CMSG_PLAYER_LOGIN)
|
||||
- ✅ Movement (CMSG_MOVE_*)
|
||||
- ✅ Chat messages (CMSG_MESSAGECHAT, SMSG_MESSAGECHAT)
|
||||
- ✅ Quest packets (CMSG_QUESTGIVER_*, SMSG_QUESTGIVER_*)
|
||||
- ✅ Vendor packets (CMSG_LIST_INVENTORY, CMSG_BUY_ITEM, CMSG_SELL_ITEM)
|
||||
- ✅ Loot packets (CMSG_LOOT, CMSG_LOOT_MONEY)
|
||||
- ✅ Spell packets (CMSG_CAST_SPELL, SMSG_SPELL_GO)
|
||||
- ✅ Inventory packets (CMSG_SWAP_INV_ITEM, CMSG_AUTOEQUIP_ITEM)
|
||||
- ✅ Gossip packets (CMSG_GOSSIP_HELLO, SMSG_GOSSIP_MESSAGE)
|
||||
- ✅ Combat packets (CMSG_ATTACKSWING, SMSG_ATTACKERSTATEUPDATE)
|
||||
|
||||
---
|
||||
|
||||
## Asset Pipeline
|
||||
|
||||
### MPQ Archives
|
||||
- ✅ StormLib integration
|
||||
- ✅ Priority-based file loading (patches override base files)
|
||||
- ✅ Locale support (enUS, enGB, deDE, frFR, etc.)
|
||||
- ✅ File existence checking
|
||||
- ✅ Data extraction with caching
|
||||
|
||||
### BLP Textures
|
||||
- ✅ BLP format parser
|
||||
- ✅ DXT1 decompression (opaque textures)
|
||||
- ✅ DXT3 decompression (sharp alpha)
|
||||
- ✅ DXT5 decompression (gradient alpha)
|
||||
- ✅ Mipmap extraction
|
||||
- ✅ OpenGL texture object creation
|
||||
- ✅ Texture caching
|
||||
|
||||
### M2 Models
|
||||
- ✅ M2 format parser (WotLK version)
|
||||
- ✅ Vertex data (position, normal, texcoord, bone weights)
|
||||
- ✅ Skeletal animation (256 bones max)
|
||||
- ✅ Animation sequences (idle, walk, run, attack, etc.)
|
||||
- ✅ Bone hierarchies and transforms
|
||||
- ✅ Particle emitters (FBlock format)
|
||||
- ✅ Render batches (multiple materials)
|
||||
- ✅ Geosets (show/hide body parts)
|
||||
- ✅ Attachment points (weapons, helmets, etc.)
|
||||
- ✅ Texture animations
|
||||
- ✅ Blend modes (opaque, alpha, additive, modulate)
|
||||
|
||||
### WMO Buildings
|
||||
- ✅ WMO format parser
|
||||
- ✅ Group-based rendering
|
||||
- ✅ Multi-material batches
|
||||
- ✅ Portal system (visibility culling)
|
||||
- ✅ Doodad placement (decorative objects)
|
||||
- ✅ Liquid data (indoor water)
|
||||
- ✅ Vertex colors
|
||||
- ✅ Distance culling (160 units)
|
||||
|
||||
### ADT Terrain
|
||||
- ✅ ADT format parser
|
||||
- ✅ 64x64 tile grid per continent
|
||||
- ✅ 16x16 chunks per tile (MCNK)
|
||||
- ✅ Height maps (9x9 + 8x8 vertices)
|
||||
- ✅ Texture layers (up to 4 per chunk)
|
||||
- ✅ Alpha blending between layers
|
||||
- ✅ Liquid data (water, lava, slime)
|
||||
- ✅ Terrain holes
|
||||
- ✅ Object placement (M2 and WMO references)
|
||||
- ✅ Async loading (prevents frame stalls)
|
||||
|
||||
### DBC Databases
|
||||
- ✅ DBC format parser
|
||||
- ✅ 20+ DBC files loaded at startup
|
||||
- ✅ String block parsing
|
||||
- ✅ Type-safe record access
|
||||
|
||||
**Loaded DBC Files:**
|
||||
- ✅ Spell.dbc - Spell data
|
||||
- ✅ SpellIcon.dbc - Spell icons
|
||||
- ✅ Item.dbc - Item definitions
|
||||
- ✅ ItemDisplayInfo.dbc - Item icons and models
|
||||
- ✅ CreatureDisplayInfo.dbc - Creature appearances
|
||||
- ✅ CreatureModelData.dbc - Creature model data
|
||||
- ✅ ChrClasses.dbc - Class information
|
||||
- ✅ ChrRaces.dbc - Race information
|
||||
- ✅ SkillLine.dbc - Skill categories
|
||||
- ✅ SkillLineAbility.dbc - Spell-to-skill mapping
|
||||
- ✅ Faction.dbc - Faction and reputation data
|
||||
- ✅ Map.dbc - Map definitions
|
||||
- ✅ AreaTable.dbc - Zone and area names
|
||||
- ✅ And more...
|
||||
|
||||
---
|
||||
|
||||
## Audio Features
|
||||
|
||||
### Music System
|
||||
- ✅ Background music playback (FFmpeg)
|
||||
- ✅ Music looping
|
||||
- ✅ Zone-specific music (TODO)
|
||||
- ✅ Combat music (TODO)
|
||||
|
||||
### Sound Effects
|
||||
- ✅ Footstep sounds
|
||||
- ✅ Surface-dependent footsteps (grass, stone, metal, etc.)
|
||||
- ✅ Combat sounds (sword swing, spell cast)
|
||||
- ✅ UI sounds (button clicks, window open/close)
|
||||
- ✅ Environmental sounds (TODO)
|
||||
|
||||
### Audio Management
|
||||
- ✅ FFmpeg integration
|
||||
- ✅ Multiple audio channels
|
||||
- ✅ Volume control (TODO - settings screen)
|
||||
- ✅ 3D positional audio (TODO)
|
||||
|
||||
---
|
||||
|
||||
## Developer Tools
|
||||
|
||||
### Debug HUD (F1)
|
||||
- ✅ FPS and frame time
|
||||
- ✅ Draw call count
|
||||
- ✅ Triangle count
|
||||
- ✅ GPU usage
|
||||
- ✅ Memory usage
|
||||
- ✅ Camera position
|
||||
- ✅ Player position
|
||||
- ✅ Current map and zone
|
||||
|
||||
### Rendering Debug
|
||||
- ✅ F2: Wireframe mode toggle
|
||||
- ✅ F9: Pause time progression
|
||||
- ✅ F10: Toggle sun/moon visibility
|
||||
- ✅ F11: Toggle star field
|
||||
- ✅ +/-: Manual time control
|
||||
- ✅ C: Toggle clouds
|
||||
- ✅ L: Toggle lens flare
|
||||
- ✅ W: Cycle weather (None/Rain/Snow)
|
||||
|
||||
### Entity Spawning
|
||||
- ✅ K: Spawn test character (M2 model)
|
||||
- ✅ J: Remove test character
|
||||
- ✅ O: Spawn test building (WMO)
|
||||
- ✅ P: Clear all spawned WMOs
|
||||
|
||||
### Logging System
|
||||
- ✅ Multi-level logging (DEBUG, INFO, WARNING, ERROR, FATAL)
|
||||
- ✅ Timestamp formatting
|
||||
- ✅ File output
|
||||
- ✅ Console output
|
||||
- ✅ Log rotation (truncate on startup)
|
||||
|
||||
### Performance Profiling
|
||||
- ✅ Frame timing
|
||||
- ✅ Draw call tracking
|
||||
- ✅ Memory allocation tracking
|
||||
- ✅ Network packet stats (TODO)
|
||||
|
||||
---
|
||||
|
||||
## Platform Support
|
||||
|
||||
### Currently Supported
|
||||
- ✅ Linux (primary development platform)
|
||||
- ✅ X11 window system
|
||||
- ✅ OpenGL 3.3 Core Profile
|
||||
|
||||
### Planned Support
|
||||
- ⏳ Windows (via Windows Subsystem)
|
||||
- ⏳ macOS (via MoltenVK for Metal support)
|
||||
- ⏳ Wayland (Linux)
|
||||
|
||||
---
|
||||
|
||||
## Technical Specifications
|
||||
|
||||
### Graphics
|
||||
- **API**: OpenGL 3.3 Core Profile
|
||||
- **Shaders**: GLSL 330
|
||||
- **Rendering**: Forward rendering with post-processing
|
||||
- **Shadow Maps**: 2048x2048 resolution
|
||||
- **Particles**: 2000 max simultaneous (weather)
|
||||
- **Bones**: 256 max per character (GPU skinning)
|
||||
|
||||
### Performance
|
||||
- **Target FPS**: 60 (VSync enabled)
|
||||
- **Typical Draw Calls**: 30-50 per frame
|
||||
- **Typical Triangles**: 50,000-100,000 per frame
|
||||
- **GPU Usage**: <10% on modern GPUs
|
||||
- **Memory**: ~500MB-1GB (depends on loaded assets)
|
||||
|
||||
### Network
|
||||
- **Protocol**: WoW 3.3.5a (build 12340)
|
||||
- **Auth Port**: 3724
|
||||
- **World Port**: 8085 (configurable)
|
||||
- **Encryption**: RC4 (header encryption)
|
||||
- **Authentication**: SRP6a
|
||||
|
||||
### Asset Requirements
|
||||
- **WoW Version**: 3.3.5a (build 12340)
|
||||
- **MPQ Files**: common.MPQ, expansion.MPQ, lichking.MPQ, patch*.MPQ
|
||||
- **Locale**: enUS (or other supported locales)
|
||||
- **Total Size**: ~15-20GB of game data
|
||||
|
||||
---
|
||||
|
||||
## Compatibility
|
||||
|
||||
### Server Compatibility
|
||||
- ✅ TrinityCore (3.3.5a branch)
|
||||
- ✅ MaNGOS (WotLK)
|
||||
- ✅ AzerothCore
|
||||
- ✅ CMaNGOS (WotLK)
|
||||
|
||||
### Build Systems
|
||||
- ✅ CMake 3.15+
|
||||
- ✅ GCC 7+ (C++17 support required)
|
||||
- ✅ Clang 6+ (C++17 support required)
|
||||
|
||||
---
|
||||
|
||||
**Last Updated**: Based on commit `06fe167` - February 2026
|
||||
|
||||
For detailed change history, see [CHANGELOG.md](CHANGELOG.md).
|
||||
For architecture details, see [docs/architecture.md](docs/architecture.md).
|
||||
For quick start guide, see [docs/quickstart.md](docs/quickstart.md).
|
||||
|
|
@ -143,14 +143,12 @@ make -j$(nproc)
|
|||
|
||||
### Getting Started
|
||||
- [Quick Start](docs/quickstart.md) -- Installation and first steps
|
||||
- [Features Overview](FEATURES.md) -- Complete feature list
|
||||
- [Changelog](CHANGELOG.md) -- Development history and recent changes
|
||||
- [Build Instructions](BUILD_INSTRUCTIONS.md) -- Detailed dependency, build, and run guide
|
||||
|
||||
### Technical Documentation
|
||||
- [Architecture](docs/architecture.md) -- System design and module overview
|
||||
- [Authentication](docs/authentication.md) -- SRP6 auth protocol details
|
||||
- [Server Setup](docs/server-setup.md) -- Local server configuration
|
||||
- [Single Player](docs/single-player.md) -- Offline mode
|
||||
- [Sky System](docs/SKY_SYSTEM.md) -- Celestial bodies, Azeroth astronomy, and WoW-accurate sky rendering
|
||||
- [SRP Implementation](docs/srp-implementation.md) -- Cryptographic details
|
||||
- [Packet Framing](docs/packet-framing.md) -- Network protocol framing
|
||||
|
|
@ -160,7 +158,7 @@ make -j$(nproc)
|
|||
|
||||
- **Graphics**: OpenGL 3.3 Core, GLSL 330, forward rendering with post-processing
|
||||
- **Performance**: 60 FPS (vsync), ~50k triangles/frame, ~30 draw calls, <10% GPU
|
||||
- **Platform**: Linux (primary), C++17, CMake 3.15+
|
||||
- **Platform**: Linux (primary), C++20, CMake 3.15+
|
||||
- **Dependencies**: SDL2, OpenGL/GLEW, GLM, OpenSSL, StormLib, ImGui, FFmpeg
|
||||
- **Architecture**: Modular design with clear separation (core, rendering, networking, game logic, asset pipeline, UI, audio)
|
||||
- **Networking**: Non-blocking TCP, SRP6a authentication, RC4 encryption, WoW 3.3.5a protocol
|
||||
|
|
|
|||
|
|
@ -1,301 +0,0 @@
|
|||
# Single-Player Mode Removal - Summary
|
||||
|
||||
## Overview
|
||||
|
||||
Successfully removed all single-player/offline functionality from the Wowee codebase, focusing exclusively on online multiplayer.
|
||||
|
||||
## Statistics
|
||||
|
||||
- **Branch**: `remove-single-player`
|
||||
- **Base**: `master` (commit 82afb83)
|
||||
- **Commits**: 4
|
||||
- **Files Changed**: 14
|
||||
- **Lines Added**: 43
|
||||
- **Lines Removed**: 3,549
|
||||
- **Net Change**: -3,506 lines
|
||||
|
||||
## Commits
|
||||
|
||||
1. **fb2e9bf** - Remove single-player mode to focus on multiplayer
|
||||
- Removed ~2,200 lines from game_handler.cpp
|
||||
- Removed SQLite database wrapper
|
||||
- Removed SP method implementations
|
||||
- Updated documentation
|
||||
|
||||
2. **82e59f7** - Remove backup file
|
||||
- Cleaned up game_handler.cpp.bak
|
||||
|
||||
3. **8377c64** - Fix compilation errors from single-player removal
|
||||
- Restored NPC animation callbacks (needed for online)
|
||||
- Removed calls to deleted methods
|
||||
- Fixed header corruption
|
||||
|
||||
4. **98c72d5** - Fix missing closing brace in update() function
|
||||
- Critical: Fixed brace balance
|
||||
- Now: 450 open, 450 close (perfect balance)
|
||||
|
||||
## Files Modified
|
||||
|
||||
### Deleted (1 file)
|
||||
- `docs/single-player.md` - 575 lines removed
|
||||
|
||||
### Modified (13 files)
|
||||
|
||||
#### Source Files
|
||||
- `src/game/game_handler.cpp` - **2,161 lines removed**
|
||||
- Removed SQLite wrapper (~700 lines)
|
||||
- Removed SP persistence (~500 lines)
|
||||
- Removed 27 SP method implementations
|
||||
- Fixed missing closing brace
|
||||
|
||||
- `src/core/application.cpp` - **534 lines removed**
|
||||
- Removed `startSinglePlayer()` method
|
||||
- Removed `teleportTo()` method
|
||||
- Removed SP member variables
|
||||
|
||||
- `src/ui/auth_screen.cpp` - 15 lines removed
|
||||
- Removed "Single-Player Mode" button
|
||||
|
||||
- `src/ui/game_screen.cpp` - 65 lines removed
|
||||
- Removed SP settings UI
|
||||
- Removed duplicate conditional logic
|
||||
- Removed calls to deleted methods
|
||||
|
||||
- `src/ui/inventory_screen.cpp` - 40 lines removed
|
||||
- Simplified to online-only logic
|
||||
- Removed SP auto-equip fallback
|
||||
|
||||
- `src/ui/character_screen.cpp` - 6 lines removed
|
||||
- Removed SP conditional check
|
||||
|
||||
#### Header Files
|
||||
- `include/game/game_handler.hpp` - 124 lines removed
|
||||
- Removed 11 public SP method declarations
|
||||
- Removed SP member variables
|
||||
- Removed SP structs (SinglePlayerSettings, SinglePlayerCreateInfo)
|
||||
- Added back NPC animation callbacks (needed for online)
|
||||
|
||||
- `include/core/application.hpp` - 18 lines removed
|
||||
- Removed SP method declarations
|
||||
- Removed SP member variables
|
||||
|
||||
- `include/ui/auth_screen.hpp` - 5 lines removed
|
||||
- Removed SP button callback
|
||||
|
||||
#### Build System
|
||||
- `CMakeLists.txt` - 9 lines removed
|
||||
- Removed SQLite3 dependency
|
||||
|
||||
#### Documentation
|
||||
- `README.md` - 9 lines changed
|
||||
- Removed SP section
|
||||
- Updated dependencies
|
||||
|
||||
- `FEATURES.md` - 28 lines removed
|
||||
- Removed SP feature list
|
||||
|
||||
- `CHANGELOG.md` - 3 lines added
|
||||
- Documented removal
|
||||
|
||||
## What Was Removed
|
||||
|
||||
### Database Layer (~700 lines)
|
||||
- SQLite3 wrapper classes
|
||||
- Character persistence
|
||||
- Inventory save/load
|
||||
- Quest state persistence
|
||||
- Settings storage
|
||||
- Loot tables
|
||||
- Item templates
|
||||
- Creature templates
|
||||
|
||||
### Game Logic (~500 lines)
|
||||
- Local combat simulation
|
||||
- SP XP calculation
|
||||
- SP damage calculation
|
||||
- NPC aggro system
|
||||
- Local loot generation
|
||||
- SP character state management
|
||||
- Dirty flag system for saves
|
||||
- Auto-save timers
|
||||
|
||||
### Methods (27 total)
|
||||
Public methods removed:
|
||||
- `setSinglePlayerCharListReady()`
|
||||
- `getSinglePlayerSettings()`
|
||||
- `setSinglePlayerSettings()`
|
||||
- `getSinglePlayerCreateInfo()`
|
||||
- `loadSinglePlayerCharacterState()`
|
||||
- `applySinglePlayerStartData()`
|
||||
- `notifyInventoryChanged()`
|
||||
- `notifyEquipmentChanged()`
|
||||
- `notifyQuestStateChanged()`
|
||||
- `flushSinglePlayerSave()`
|
||||
- `setSinglePlayerMode()`
|
||||
- `isSinglePlayerMode()`
|
||||
- `simulateMotd()`
|
||||
- `getLocalPlayerHealth()`
|
||||
- `getLocalPlayerMaxHealth()`
|
||||
- `initLocalPlayerStats()`
|
||||
- `getItemTemplateName()`
|
||||
- `getItemTemplateQuality()`
|
||||
|
||||
Private methods removed:
|
||||
- `generateLocalLoot()`
|
||||
- `simulateLootResponse()`
|
||||
- `simulateLootRelease()`
|
||||
- `simulateLootRemove()`
|
||||
- `simulateXpGain()`
|
||||
- `updateLocalCombat()`
|
||||
- `updateNpcAggro()`
|
||||
- `performPlayerSwing()`
|
||||
- `performNpcSwing()`
|
||||
- `handleNpcDeath()`
|
||||
- `aggroNpc()`
|
||||
- `isNpcAggroed()`
|
||||
- `awardLocalXp()`
|
||||
- `levelUp()`
|
||||
- `markSinglePlayerDirty()`
|
||||
- `loadSinglePlayerCharacters()`
|
||||
- `saveSinglePlayerCharacterState()`
|
||||
|
||||
### UI Elements
|
||||
- "Single-Player Mode" button on auth screen
|
||||
- SP settings panel in game screen
|
||||
- Teleportation preset buttons
|
||||
- SP-specific tooltips and labels
|
||||
|
||||
### Member Variables (~40)
|
||||
- `singlePlayerMode_` flag
|
||||
- `spDirtyFlags_`, `spDirtyHighPriority_`
|
||||
- `spDirtyTimer_`, `spPeriodicTimer_`
|
||||
- `localPlayerHealth_`, `localPlayerMaxHealth_`, `localPlayerLevel_`
|
||||
- `swingTimer_`, `aggroList_`
|
||||
- `spHasState_`, `spSavedOrientation_`
|
||||
- `spSettings_`, `spSettingsLoaded_`
|
||||
- Plus 8+ spawn preset variables in application.cpp
|
||||
|
||||
## What Was Preserved (100%)
|
||||
|
||||
### Online Features
|
||||
✅ Authentication (SRP6a with RC4)
|
||||
✅ Realm selection
|
||||
✅ Character creation/deletion/selection
|
||||
✅ World entry
|
||||
✅ Movement (WASD, spline paths)
|
||||
✅ Combat (auto-attack, spell casting)
|
||||
✅ Targeting system
|
||||
✅ Inventory & equipment (23 slots + 16 backpack)
|
||||
✅ Action bar (12 slots with keybindings)
|
||||
✅ Spellbook (class specialty tabs)
|
||||
✅ Quest system (markers, log, turn-in)
|
||||
✅ Vendor system (buy/sell)
|
||||
✅ Loot system
|
||||
✅ Gossip/NPC interaction
|
||||
✅ Chat system (SAY, YELL, WHISPER)
|
||||
✅ Party/group system
|
||||
✅ XP tracking
|
||||
✅ Auras/buffs
|
||||
|
||||
### Rendering
|
||||
✅ Terrain streaming
|
||||
✅ Water rendering
|
||||
✅ Sky/celestial system
|
||||
✅ Weather effects
|
||||
✅ Character rendering
|
||||
✅ M2 models with animations
|
||||
✅ WMO buildings
|
||||
✅ Particle emitters
|
||||
✅ Post-processing (HDR, shadows)
|
||||
|
||||
### Callbacks (Preserved)
|
||||
✅ `NpcDeathCallback` - triggers death animations
|
||||
✅ `NpcRespawnCallback` - resets to idle on respawn
|
||||
✅ `MeleeSwingCallback` - player melee animation
|
||||
✅ `NpcSwingCallback` - NPC attack animation
|
||||
✅ `WorldEntryCallback` - world entry event
|
||||
✅ `CreatureSpawnCallback` - creature spawn event
|
||||
✅ `CreatureDespawnCallback` - creature despawn event
|
||||
✅ `CreatureMoveCallback` - creature movement
|
||||
|
||||
## Code Quality
|
||||
|
||||
### Before
|
||||
- 4,921 lines in game_handler.cpp
|
||||
- 779 opening braces, 779 closing braces
|
||||
- 20+ `singlePlayerMode_` conditional branches
|
||||
- SQLite3 build dependency
|
||||
|
||||
### After
|
||||
- 2,795 lines in game_handler.cpp (-43%)
|
||||
- 450 opening braces, 450 closing braces
|
||||
- 0 `singlePlayerMode_` references
|
||||
- No SQLite3 dependency
|
||||
|
||||
### Verification
|
||||
```bash
|
||||
# Brace balance
|
||||
grep -c "{" src/game/game_handler.cpp # 450
|
||||
grep -c "}" src/game/game_handler.cpp # 450
|
||||
|
||||
# SP references
|
||||
grep -ri "singleplayer" src/ include/ # 0 matches
|
||||
grep -ri "sqlite" src/ include/ # 0 matches
|
||||
```
|
||||
|
||||
## Testing Required
|
||||
|
||||
Before merging to master:
|
||||
- [ ] Build succeeds
|
||||
- [ ] Application launches
|
||||
- [ ] Auth to server works
|
||||
- [ ] Can view characters
|
||||
- [ ] Can create character
|
||||
- [ ] Can enter world
|
||||
- [ ] Movement works
|
||||
- [ ] Combat works
|
||||
- [ ] Inventory works
|
||||
- [ ] Quests work
|
||||
- [ ] Loot works
|
||||
- [ ] No crashes
|
||||
|
||||
## Migration Path
|
||||
|
||||
For users on master branch:
|
||||
```bash
|
||||
# Current state preserved in master
|
||||
git checkout master
|
||||
|
||||
# New online-only version
|
||||
git checkout remove-single-player
|
||||
|
||||
# Test, then merge when satisfied
|
||||
git checkout master
|
||||
git merge remove-single-player
|
||||
```
|
||||
|
||||
## Performance Impact
|
||||
|
||||
Expected improvements:
|
||||
- **Memory**: ~2MB less (no SQLite, no SP state)
|
||||
- **Startup**: Slightly faster (no DB init)
|
||||
- **Update loop**: Cleaner (no SP simulation)
|
||||
- **Disk I/O**: None (no save files)
|
||||
|
||||
## Breaking Changes
|
||||
|
||||
⚠️ **Incompatible with master branch saves**
|
||||
- No save files in remove-single-player branch
|
||||
- All state is server-side only
|
||||
- Cannot load SP saves (none exist)
|
||||
|
||||
## Credits
|
||||
|
||||
Implementation by Claude (Anthropic)
|
||||
Date: 2026-02-07
|
||||
Task: Remove single-player mode, focus on multiplayer
|
||||
|
||||
---
|
||||
|
||||
**Status**: ✅ Complete and ready to build
|
||||
**Next**: Install dependencies and compile
|
||||
|
|
@ -1,299 +0,0 @@
|
|||
#include "audio/npc_voice_manager.hpp"
|
||||
#include "audio/audio_engine.hpp"
|
||||
#include "pipeline/asset_manager.hpp"
|
||||
#include "core/logger.hpp"
|
||||
#include <glm/glm.hpp>
|
||||
|
||||
namespace wowee {
|
||||
namespace audio {
|
||||
|
||||
NpcVoiceManager::NpcVoiceManager() : rng_(std::random_device{}()) {}
|
||||
|
||||
NpcVoiceManager::~NpcVoiceManager() {
|
||||
shutdown();
|
||||
}
|
||||
|
||||
bool NpcVoiceManager::initialize(pipeline::AssetManager* assets) {
|
||||
assetManager_ = assets;
|
||||
if (!assetManager_) {
|
||||
LOG_WARNING("NPC voice manager: no asset manager");
|
||||
return false;
|
||||
}
|
||||
|
||||
// Files are .WAV not .OGG in WotLK 3.3.5a!
|
||||
LOG_INFO("=== Probing for NPC voice files (.wav format) ===");
|
||||
std::vector<std::string> testPaths = {
|
||||
"Sound\\Creature\\HumanMaleStandardNPC\\HumanMaleStandardNPCGreetings01.wav",
|
||||
"Sound\\Creature\\HumanFemaleStandardNPC\\HumanFemaleStandardNPCGreeting01.wav",
|
||||
"Sound\\Creature\\DwarfMaleStandardNPC\\DwarfMaleStandardNPCGreeting01.wav",
|
||||
"Sound\\Creature\\OrcMaleStandardNPC\\OrcMaleStandardNPCGreeting01.wav",
|
||||
};
|
||||
for (const auto& path : testPaths) {
|
||||
bool exists = assetManager_->fileExists(path);
|
||||
LOG_INFO(" ", path, ": ", (exists ? "EXISTS" : "NOT FOUND"));
|
||||
}
|
||||
LOG_INFO("=== Probing for tavern music files ===");
|
||||
std::vector<std::string> musicPaths = {
|
||||
"Sound\\Music\\GlueScreenMusic\\tavern_01.mp3",
|
||||
"Sound\\Music\\GlueScreenMusic\\BC_Alehouse.mp3",
|
||||
"Sound\\Music\\ZoneMusic\\Tavern\\tavernAlliance01.mp3",
|
||||
};
|
||||
for (const auto& path : musicPaths) {
|
||||
bool exists = assetManager_->fileExists(path);
|
||||
LOG_INFO(" ", path, ": ", (exists ? "EXISTS" : "NOT FOUND"));
|
||||
}
|
||||
LOG_INFO("===================================");
|
||||
|
||||
loadVoiceSounds();
|
||||
|
||||
int totalSamples = 0;
|
||||
for (const auto& [type, samples] : voiceLibrary_) {
|
||||
totalSamples += samples.size();
|
||||
}
|
||||
LOG_INFO("NPC voice manager initialized (", totalSamples, " voice clips)");
|
||||
return true;
|
||||
}
|
||||
|
||||
void NpcVoiceManager::shutdown() {
|
||||
voiceLibrary_.clear();
|
||||
lastPlayTime_.clear();
|
||||
assetManager_ = nullptr;
|
||||
}
|
||||
|
||||
void NpcVoiceManager::loadVoiceSounds() {
|
||||
if (!assetManager_) return;
|
||||
|
||||
// WotLK 3.3.5a uses .WAV files, not .OGG!
|
||||
// Files use "Greeting" (singular) not "Greetings"
|
||||
|
||||
// Generic - mix of all races for variety
|
||||
auto& genericVoices = voiceLibrary_[VoiceType::GENERIC];
|
||||
for (const auto& path : {
|
||||
"Sound\\Creature\\HumanMaleStandardNPC\\HumanMaleStandardNPCGreetings01.wav",
|
||||
"Sound\\Creature\\HumanFemaleStandardNPC\\HumanFemaleStandardNPCGreeting01.wav",
|
||||
"Sound\\Creature\\DwarfMaleStandardNPC\\DwarfMaleStandardNPCGreeting01.wav",
|
||||
"Sound\\Creature\\GnomeMaleStandardNPC\\GnomeMaleStandardNPCGreeting01.wav",
|
||||
"Sound\\Creature\\NightElfMaleStandardNPC\\NightElfMaleStandardNPCGreeting01.wav",
|
||||
"Sound\\Creature\\OrcMaleStandardNPC\\OrcMaleStandardNPCGreeting01.wav",
|
||||
}) {
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) genericVoices.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Human Male (uses "Greetings" plural)
|
||||
auto& humanMale = voiceLibrary_[VoiceType::HUMAN_MALE];
|
||||
for (int i = 1; i <= 6; ++i) {
|
||||
std::string path = "Sound\\Creature\\HumanMaleStandardNPC\\HumanMaleStandardNPCGreetings0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) humanMale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Human Female
|
||||
auto& humanFemale = voiceLibrary_[VoiceType::HUMAN_FEMALE];
|
||||
for (int i = 1; i <= 5; ++i) {
|
||||
std::string path = "Sound\\Creature\\HumanFemaleStandardNPC\\HumanFemaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) humanFemale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Dwarf Male
|
||||
auto& dwarfMale = voiceLibrary_[VoiceType::DWARF_MALE];
|
||||
for (int i = 1; i <= 6; ++i) {
|
||||
std::string path = "Sound\\Creature\\DwarfMaleStandardNPC\\DwarfMaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) dwarfMale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Gnome Male
|
||||
auto& gnomeMale = voiceLibrary_[VoiceType::GNOME_MALE];
|
||||
for (int i = 1; i <= 6; ++i) {
|
||||
std::string path = "Sound\\Creature\\GnomeMaleStandardNPC\\GnomeMaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) gnomeMale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Gnome Female
|
||||
auto& gnomeFemale = voiceLibrary_[VoiceType::GNOME_FEMALE];
|
||||
for (int i = 1; i <= 6; ++i) {
|
||||
std::string path = "Sound\\Creature\\GnomeFemaleStandardNPC\\GnomeFemaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) gnomeFemale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Night Elf Male
|
||||
auto& nelfMale = voiceLibrary_[VoiceType::NIGHTELF_MALE];
|
||||
for (int i = 1; i <= 8; ++i) {
|
||||
std::string path = "Sound\\Creature\\NightElfMaleStandardNPC\\NightElfMaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) nelfMale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Night Elf Female
|
||||
auto& nelfFemale = voiceLibrary_[VoiceType::NIGHTELF_FEMALE];
|
||||
for (int i = 1; i <= 6; ++i) {
|
||||
std::string path = "Sound\\Creature\\NightElfFemaleStandardNPC\\NightElfFemaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) nelfFemale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Orc Male
|
||||
auto& orcMale = voiceLibrary_[VoiceType::ORC_MALE];
|
||||
for (int i = 1; i <= 5; ++i) {
|
||||
std::string path = "Sound\\Creature\\OrcMaleStandardNPC\\OrcMaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) orcMale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Orc Female
|
||||
auto& orcFemale = voiceLibrary_[VoiceType::ORC_FEMALE];
|
||||
for (int i = 1; i <= 6; ++i) {
|
||||
std::string path = "Sound\\Creature\\OrcFemaleStandardNPC\\OrcFemaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) orcFemale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Tauren Male
|
||||
auto& taurenMale = voiceLibrary_[VoiceType::TAUREN_MALE];
|
||||
for (int i = 1; i <= 5; ++i) {
|
||||
std::string path = "Sound\\Creature\\TaurenMaleStandardNPC\\TaurenMaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) taurenMale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Tauren Female
|
||||
auto& taurenFemale = voiceLibrary_[VoiceType::TAUREN_FEMALE];
|
||||
for (int i = 1; i <= 5; ++i) {
|
||||
std::string path = "Sound\\Creature\\TaurenFemaleStandardNPC\\TaurenFemaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) taurenFemale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Troll Male
|
||||
auto& trollMale = voiceLibrary_[VoiceType::TROLL_MALE];
|
||||
for (int i = 1; i <= 6; ++i) {
|
||||
std::string path = "Sound\\Creature\\TrollMaleStandardNPC\\TrollMaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) trollMale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Troll Female
|
||||
auto& trollFemale = voiceLibrary_[VoiceType::TROLL_FEMALE];
|
||||
for (int i = 1; i <= 5; ++i) {
|
||||
std::string path = "Sound\\Creature\\TrollFemaleStandardNPC\\TrollFemaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) trollFemale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Undead Male
|
||||
auto& undeadMale = voiceLibrary_[VoiceType::UNDEAD_MALE];
|
||||
for (int i = 1; i <= 6; ++i) {
|
||||
std::string path = "Sound\\Creature\\UndeadMaleStandardNPC\\UndeadMaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) undeadMale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Undead Female
|
||||
auto& undeadFemale = voiceLibrary_[VoiceType::UNDEAD_FEMALE];
|
||||
for (int i = 1; i <= 6; ++i) {
|
||||
std::string path = "Sound\\Creature\\UndeadFemaleStandardNPC\\UndeadFemaleStandardNPCGreeting0" + std::to_string(i) + ".wav";
|
||||
VoiceSample sample;
|
||||
if (loadSound(path, sample)) undeadFemale.push_back(std::move(sample));
|
||||
}
|
||||
|
||||
// Log loaded voice types
|
||||
int totalLoaded = 0;
|
||||
for (const auto& [type, samples] : voiceLibrary_) {
|
||||
if (!samples.empty()) {
|
||||
LOG_INFO("Loaded ", samples.size(), " voice samples for type ", static_cast<int>(type));
|
||||
totalLoaded += samples.size();
|
||||
}
|
||||
}
|
||||
|
||||
if (totalLoaded == 0) {
|
||||
LOG_WARNING("NPC voice manager: no voice samples loaded (files may not exist in MPQ)");
|
||||
}
|
||||
}
|
||||
|
||||
bool NpcVoiceManager::loadSound(const std::string& path, VoiceSample& sample) {
|
||||
if (!assetManager_ || !assetManager_->fileExists(path)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
auto data = assetManager_->readFile(path);
|
||||
if (data.empty()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
sample.path = path;
|
||||
sample.data = std::move(data);
|
||||
return true;
|
||||
}
|
||||
|
||||
void NpcVoiceManager::playGreeting(uint64_t npcGuid, VoiceType voiceType, const glm::vec3& position) {
|
||||
LOG_INFO("NPC voice: playGreeting called for GUID ", npcGuid);
|
||||
|
||||
if (!AudioEngine::instance().isInitialized()) {
|
||||
LOG_WARNING("NPC voice: AudioEngine not initialized");
|
||||
return;
|
||||
}
|
||||
|
||||
// Check cooldown
|
||||
auto now = std::chrono::steady_clock::now();
|
||||
auto it = lastPlayTime_.find(npcGuid);
|
||||
if (it != lastPlayTime_.end()) {
|
||||
float elapsed = std::chrono::duration<float>(now - it->second).count();
|
||||
if (elapsed < GREETING_COOLDOWN) {
|
||||
LOG_INFO("NPC voice: on cooldown (", elapsed, "s elapsed)");
|
||||
return; // Still on cooldown
|
||||
}
|
||||
}
|
||||
|
||||
// Find voice library for this type
|
||||
auto libIt = voiceLibrary_.find(voiceType);
|
||||
if (libIt == voiceLibrary_.end() || libIt->second.empty()) {
|
||||
LOG_INFO("NPC voice: No samples for type ", static_cast<int>(voiceType), ", falling back to GENERIC");
|
||||
// Fall back to generic
|
||||
libIt = voiceLibrary_.find(VoiceType::GENERIC);
|
||||
if (libIt == voiceLibrary_.end() || libIt->second.empty()) {
|
||||
LOG_WARNING("NPC voice: No voice samples available (library empty)");
|
||||
return; // No voice samples available
|
||||
}
|
||||
}
|
||||
|
||||
const auto& samples = libIt->second;
|
||||
|
||||
// Pick random voice line
|
||||
std::uniform_int_distribution<size_t> dist(0, samples.size() - 1);
|
||||
const auto& sample = samples[dist(rng_)];
|
||||
|
||||
LOG_INFO("NPC voice: Playing sound from: ", sample.path);
|
||||
|
||||
// Play with 3D positioning
|
||||
std::uniform_real_distribution<float> volumeDist(0.85f, 1.0f);
|
||||
std::uniform_real_distribution<float> pitchDist(0.98f, 1.02f);
|
||||
|
||||
bool success = AudioEngine::instance().playSound3D(
|
||||
sample.data,
|
||||
position,
|
||||
volumeDist(rng_) * volumeScale_,
|
||||
pitchDist(rng_),
|
||||
40.0f // Max distance for voice
|
||||
);
|
||||
|
||||
if (success) {
|
||||
LOG_INFO("NPC voice: Sound played successfully");
|
||||
lastPlayTime_[npcGuid] = now;
|
||||
} else {
|
||||
LOG_WARNING("NPC voice: Failed to play sound");
|
||||
}
|
||||
}
|
||||
|
||||
VoiceType NpcVoiceManager::detectVoiceType(uint32_t creatureEntry) const {
|
||||
// TODO: Use CreatureTemplate.dbc or other data to map creature entry to voice type
|
||||
// For now, return generic
|
||||
(void)creatureEntry;
|
||||
return VoiceType::GENERIC;
|
||||
}
|
||||
|
||||
} // namespace audio
|
||||
} // namespace wowee
|
||||
|
|
@ -1,36 +0,0 @@
|
|||
#!/bin/bash
|
||||
# Test script for ambient audio debugging
|
||||
|
||||
echo "=== Testing Ambient Audio System ==="
|
||||
echo ""
|
||||
echo "Running game for 60 seconds and capturing logs..."
|
||||
echo ""
|
||||
|
||||
timeout 60 build/bin/wowee 2>&1 | tee /tmp/wowee_ambient_test.log
|
||||
|
||||
echo ""
|
||||
echo "=== Analysis ==="
|
||||
echo ""
|
||||
|
||||
echo "1. AmbientSoundManager Initialization:"
|
||||
grep -i "AmbientSoundManager" /tmp/wowee_ambient_test.log | head -20
|
||||
echo ""
|
||||
|
||||
echo "2. Fire Emitters Detected:"
|
||||
grep -i "fire emitter" /tmp/wowee_ambient_test.log
|
||||
echo ""
|
||||
|
||||
echo "3. Water Emitters Registered:"
|
||||
grep -i "water.*emitter" /tmp/wowee_ambient_test.log | head -10
|
||||
echo ""
|
||||
|
||||
echo "4. Sample WMO Doodads Loaded:"
|
||||
grep "WMO doodad:" /tmp/wowee_ambient_test.log | head -20
|
||||
echo ""
|
||||
|
||||
echo "5. Total Ambient Emitters:"
|
||||
grep "Registered.*ambient" /tmp/wowee_ambient_test.log
|
||||
echo ""
|
||||
|
||||
echo "Full log saved to: /tmp/wowee_ambient_test.log"
|
||||
echo "Use 'grep <keyword> /tmp/wowee_ambient_test.log' to search for specific issues"
|
||||
|
|
@ -1,36 +0,0 @@
|
|||
#include <iostream>
|
||||
#include "pipeline/dbc.hpp"
|
||||
#include "pipeline/asset_manager.hpp"
|
||||
|
||||
int main() {
|
||||
wowee::pipeline::AssetManager assetManager;
|
||||
assetManager.initialize("Data");
|
||||
|
||||
auto godi = assetManager.loadDBC("GameObjectDisplayInfo.dbc");
|
||||
if (!godi || !godi->isLoaded()) {
|
||||
std::cerr << "Failed to load GameObjectDisplayInfo.dbc\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
std::cout << "GameObjectDisplayInfo.dbc loaded with " << godi->getRecordCount() << " records\n\n";
|
||||
|
||||
// Check displayIds 35 and 1287
|
||||
uint32_t targetIds[] = {35, 1287};
|
||||
for (uint32_t targetId : targetIds) {
|
||||
bool found = false;
|
||||
for (uint32_t i = 0; i < godi->getRecordCount(); i++) {
|
||||
uint32_t displayId = godi->getUInt32(i, 0);
|
||||
if (displayId == targetId) {
|
||||
std::string modelName = godi->getString(i, 1);
|
||||
std::cout << "DisplayId " << displayId << ": " << modelName << "\n";
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!found) {
|
||||
std::cout << "DisplayId " << targetId << ": NOT FOUND\n";
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -1,25 +0,0 @@
|
|||
#!/bin/bash
|
||||
# Test if splash sounds load properly
|
||||
|
||||
echo "Testing splash sound files..."
|
||||
echo ""
|
||||
|
||||
for file in \
|
||||
"Sound\\Character\\Footsteps\\EnterWaterSplash\\EnterWaterSmallA.wav" \
|
||||
"Sound\\Character\\Footsteps\\EnterWaterSplash\\EnterWaterMediumA.wav" \
|
||||
"Sound\\Character\\Footsteps\\EnterWaterSplash\\EnterWaterGiantA.wav" \
|
||||
"Sound\\Character\\Footsteps\\WaterSplash\\FootStepsMediumWaterA.wav"
|
||||
do
|
||||
echo -n "Checking: $file ... "
|
||||
if ./list_mpq Data/common.MPQ "$file" 2>/dev/null | grep -q "wav"; then
|
||||
echo "✓ EXISTS"
|
||||
else
|
||||
echo "✗ NOT FOUND"
|
||||
fi
|
||||
done
|
||||
|
||||
echo ""
|
||||
echo "Now run the game and check for:"
|
||||
echo " Activity SFX loaded: jump=X splash=8 swimLoop=X"
|
||||
echo ""
|
||||
echo "If splash=0, the files aren't being loaded by ActivitySoundManager"
|
||||
Loading…
Add table
Add a link
Reference in a new issue