๐ค AI-Powered VR Secretary โ Production-ready reference implementation combining Unreal Engine 5 VR, local/cloud LLMs, and high-quality TTS for fully interactive virtual assistants in VR.
Features โข Quick Start โข Documentation โข Architecture โข Contributing
- What Is VRSecretary?
- Key Features
- System Requirements
- Quick Start Guide
- Repository Structure
- Backend Configuration
- Unreal Plugin Setup
- AI Persona: Ailey
- Avatar Assets
- Development & Testing
- Architecture Overview
- Troubleshooting
- Documentation
- Contributing
- License
- Acknowledgments
VRSecretary is a production-ready, open-source reference architecture for building AI-powered conversational characters in VR. It combines cutting-edge language models with spatial audio and immersive interaction to create a natural, engaging virtual assistant experience.
- Frontend: Unreal Engine 5 (VR-native, supports Meta Quest, PCVR, and more)
- Backend: Python FastAPI (modular, extensible, engine-agnostic)
- LLM: Flexible backend support:
- Local: Ollama (llama3, Mistral, Granite, etc.)
- Cloud: IBM watsonx.ai
- In-Engine: llama.cpp via Llama-Unreal plugin
- TTS: Chatterbox (natural-sounding, sentence-aware streaming)
โ
Complete Unreal Engine 5 VR project with sample secretary character
โ
Production-ready plugin (VRSecretary) with Blueprint support
โ
FastAPI gateway backend with clean REST API
โ
Sample 3D avatar (Scifi Girl v.01 - non-commercial demo)
โ
Comprehensive documentation and integration guides
โ
Multiple backend modes (Gateway, Direct Ollama, Local Llama.cpp)
โ
Docker support for easy deployment
โ
Load testing tools and performance benchmarks
- Full 6DOF interaction with VR controllers
- 3D spatial audio that follows the character
- Real-time subtitles floating above the avatar
- Teleportation and smooth locomotion support
- Hand presence and gesture recognition ready
| Mode | Description | Use Case |
|---|---|---|
| Gateway (Ollama) | FastAPI โ Ollama โ TTS โ UE | Local development, full features |
| Gateway (watsonx) | FastAPI โ watsonx.ai โ TTS โ UE | Cloud deployment, enterprise |
| Direct Ollama | UE โ OpenAI-style API โ UE | Text-only, simple integration |
| Local Llama.cpp | UE โ in-engine llama.cpp โ UE | Offline, embedded deployment |
- Sentence-aware streaming for natural pacing
- Configurable voice parameters (temperature, speed, exaggeration)
- Multiple voice profiles (female/male, extensible)
- CUDA/MPS acceleration for real-time generation
- EOS-safe chunking prevents audio artifacts
- Engine-agnostic REST API (Unity, Godot, Web can use same backend)
- Session management with conversation history
- Comprehensive error handling and logging
- Configurable via environment variables and Project Settings
- Dockerized deployment with compose files
- Load testing scripts included
- Clean separation of concerns (backend, plugin, assets)
- Blueprint-friendly components for rapid prototyping
- C++ API for advanced customization
- Plugin system for adding new LLM/TTS providers
- Multiple language support ready
| Component | Specification |
|---|---|
| OS | Windows 10/11 (recommended), Linux/macOS (backend only) |
| CPU | Quad-core Intel/AMD, 2.5 GHz+ |
| RAM | 16 GB |
| GPU | NVIDIA GTX 1060 or equivalent (for VR) |
| Storage | 30 GB free space (SSD recommended) |
| VR Headset | Meta Quest 2/3, Valve Index, or compatible PCVR |
| Component | Specification |
|---|---|
| CPU | 8-core Intel i7/AMD Ryzen 7, 3.5 GHz+ |
| RAM | 32 GB |
| GPU | NVIDIA RTX 3060 or better (CUDA for LLM/TTS acceleration) |
| Storage | 50 GB free space on NVMe SSD |
Required:
- Unreal Engine 5.3 or later (with C++ source access)
- Visual Studio 2022 (Windows) with "Game development with C++" workload
- Python 3.10 or later
- Git (for cloning repository)
Optional:
- Docker Desktop (for containerized backend)
- Node.js & k6 (for load testing)
- CUDA Toolkit 11.8+ (for GPU acceleration)
Get from zero to working VR secretary in ~30 minutes.
git clone https://github.com/ruslanmv/VRSecretary.git
cd VRSecretaryDownload and install from https://ollama.ai/
# Start Ollama server
ollama serve
# In a new terminal, download a model
ollama pull llama3Verify:
curl http://localhost:11434/v1/modelscd backend/gateway
# Create virtual environment
python -m venv .venv
# Activate (Windows PowerShell)
.venv\Scripts\Activate.ps1
# Activate (Linux/macOS)
# source .venv/bin/activate
# Install dependencies
pip install -e .# Copy template
cp ../docker/env.example .env
# Edit .env with your preferred editorMinimal .env configuration:
MODE=offline_local_ollama
OLLAMA_BASE_URL=http://localhost:11434
OLLAMA_MODEL=llama3
OLLAMA_TIMEOUT=60.0
CHATTERBOX_URL=http://localhost:4123
CHATTERBOX_TIMEOUT=30.0
SESSION_MAX_HISTORY=10uvicorn vrsecretary_gateway.main:app --reload --host 0.0.0.0 --port 8000Verify backend is running:
- API docs: http://localhost:8000/docs
- Health check: http://localhost:8000/health
In a new terminal (keep gateway running):
# From repo root
cd VRSecretary
# Activate same venv
backend/gateway/.venv/Scripts/Activate.ps1 # Windows
# source backend/gateway/.venv/bin/activate # Linux/macOS
# Start Chatterbox TTS server
python tools/vr_chatterbox_server.py --host 0.0.0.0 --port 4123Optional environment variables:
# Force CUDA (default: auto-detect)
export CHATTERBOX_DEVICE=cuda
# Chunk size for streaming (default: 20 words)
export CHATTERBOX_CHUNK_SIZE=20
# Custom voice files (optional)
export CHATTERBOX_FEMALE_VOICE=/path/to/female_voice.wav
export CHATTERBOX_MALE_VOICE=/path/to/male_voice.wavTest TTS (PowerShell):
Invoke-WebRequest `
-Uri "http://localhost:4123/v1/audio/speech" `
-Method POST `
-ContentType "application/json" `
-Body '{"input": "Hello from Ailey.", "voice": "female"}' `
-OutFile "test.wav"Test TTS (curl):
curl -X POST http://localhost:4123/v1/audio/speech \
-H "Content-Type: application/json" \
-d '{"input": "Hello from Ailey.", "voice": "female"}' \
--output test.wavPlay test.wav to verify audio quality.
With all three services running (Ollama, Gateway, TTS):
curl -X POST http://localhost:8000/api/vr_chat \
-H "Content-Type: application/json" \
-d '{"session_id": "test-123", "user_text": "Hello Ailey, introduce yourself."}'Expected response:
{
"assistant_text": "Hi! I'm Ailey, your VR secretary. I'm here to help...",
"audio_wav_base64": "UklGRiQAAABXQVZF..."
}โ If you see text and base64 audio, the backend is working!
Navigate to:
VRSecretary/samples/unreal-vr-secretary-demo/
Right-click VRSecretaryDemo.uproject โ Generate Visual Studio project files
Double-click VRSecretaryDemo.uproject
Unreal will:
- Compile C++ modules (including VRSecretary plugin)
- Load the project (first time may take 5-10 minutes)
- Edit โ Plugins
- Search:
VRSecretary - โ Check Enabled (should already be checked)
- Restart editor if prompted
- Edit โ Project Settings
- Navigate to: Plugins โ VRSecretary
- Set:
- Gateway URL:
http://localhost:8000 - Backend Mode:
Gateway (Ollama) - HTTP Timeout:
60.0 - Language Code: (leave empty for English)
- Gateway URL:
VRSecretary/assets/avatars/scifi_girl_v01/scifi_girl_v.01.glb
- In Content Browser, navigate to:
/Game/Characters/ScifiGirl/ - Right-click โ Import to /Game/Characters/ScifiGirl/
- Select
scifi_girl_v.01.glb - Import Settings:
- โ Import Mesh
- โ Import Skeletal Mesh
- โ Import Materials
- โ Import Textures
- Click Import All
Open BP_SecretaryAvatar:
- Components panel โ Select Mesh component
- Details panel โ Mesh โ Select imported skeletal mesh
- Adjust Transform if needed (scale, rotation)
- Compile and Save
- Meta Quest: Enable developer mode, connect via Link/Air Link
- PCVR: Connect via SteamVR or native runtime
- Click Play dropdown (top toolbar)
- Select VR Preview
- Put on headset
Desktop Mode (testing without VR):
- Press T key โ Opens chat interface
- Type message โ Press Enter
- See subtitle above character
- Hear audio response
VR Mode:
- Press Right Trigger โ Opens 3D chat panel
- Point laser at text field โ Click trigger to focus
- Use VR keyboard or voice input (if configured)
- Press trigger on Send button
Expected behavior:
- Your message appears in chat
- Subtitle appears above Ailey's head
- Audio plays from character position (3D spatial)
- Response text appears in chat history
VRSecretary/
โโโ ๐ assets/
โ โโโ ๐ avatars/
โ โโโ ๐ scifi_girl_v01/
โ โโโ scifi_girl_v.01.glb # Sample avatar (CC BY-NC-SA)
โ โโโ README.md # License & attribution
โ โโโ DOWNLOAD_INSTRUCTIONS.txt
โ
โโโ ๐ backend/
โ โโโ ๐ gateway/ # FastAPI backend
โ โ โโโ pyproject.toml # Python dependencies
โ โ โโโ README.md # Backend docs
โ โ โโโ ๐ vrsecretary_gateway/
โ โ โโโ main.py # FastAPI app entrypoint
โ โ โโโ config.py # Settings (Pydantic)
โ โ โโโ ๐ api/ # REST endpoints
โ โ โ โโโ health_router.py
โ โ โ โโโ vr_chat_router.py
โ โ โโโ ๐ llm/ # LLM clients
โ โ โ โโโ base_client.py
โ โ โ โโโ ollama_client.py
โ โ โ โโโ watsonx_client.py
โ โ โโโ ๐ tts/ # TTS integration
โ โ โ โโโ chatterbox_client.py
โ โ โโโ ๐ models/ # Request/response schemas
โ โ โโโ chat_models.py
โ โ โโโ session_store.py
โ โโโ ๐ docker/
โ โโโ Dockerfile.gateway
โ โโโ docker-compose.dev.yml
โ โโโ env.example
โ
โโโ ๐ engine-plugins/
โ โโโ ๐ unreal/
โ โโโ ๐ VRSecretary/ # Main Unreal plugin
โ โโโ VRSecretary.uplugin
โ โโโ README.md # Plugin documentation
โ โโโ ๐ Source/VRSecretary/
โ โ โโโ VRSecretary.Build.cs
โ โ โโโ ๐ Public/
โ โ โ โโโ VRSecretaryComponent.h # Main component
โ โ โ โโโ VRSecretarySettings.h # Project settings
โ โ โ โโโ VRSecretaryChatTypes.h # Enums, structs
โ โ โ โโโ VRSecretaryLog.h
โ โ โโโ ๐ Private/
โ โ โโโ VRSecretaryModule.cpp
โ โ โโโ VRSecretaryComponent.cpp
โ โ โโโ VRSecretarySettings.cpp
โ โ โโโ VRSecretaryLog.cpp
โ โโโ ๐ ThirdParty/
โ โโโ ๐ LlamaCpp/ # Optional llama.cpp
โ
โโโ ๐ samples/
โ โโโ ๐ unreal-vr-secretary-demo/ # Example UE5 project
โ โ โโโ VRSecretaryDemo.uproject
โ โ โโโ ๐ Config/
โ โ โ โโโ DefaultEngine.ini
โ โ โโโ ๐ Content/
โ โ โโโ ๐ Blueprints/ # BP_VRPawn, BP_DesktopPlayer
โ โ โโโ ๐ UI/ # WBP_ChatInterface
โ โ โโโ ๐ Characters/ # BP_SecretaryAvatar
โ โ โโโ ๐ Maps/ # VRSecretaryLevel
โ โโโ ๐ backend-notebooks/
โ โโโ prototype-calls.ipynb
โ
โโโ ๐ docs/
โ โโโ overview.md
โ โโโ architecture.md
โ โโโ unreal-integration.md # Step-by-step UE setup
โ โโโ engine-agnostic-api.md # REST API reference
โ โโโ persona-ailey.md # Customizing AI behavior
โ โโโ troubleshooting.md
โ
โโโ ๐ tools/
โ โโโ ๐ scripts/
โ โ โโโ start_local_stack.sh
โ โ โโโ generate_openapi_client.sh
โ โโโ ๐ perf/
โ โ โโโ load_test_vr_chat.k6.js # k6 load tests
โ โ โโโ profiling_notes.md
โ โโโ vr_chatterbox_server.py # Optimized TTS server
โ
โโโ ๐ .github/
โ โโโ ๐ workflows/ # CI/CD
โ โ โโโ backend-tests.yml
โ โ โโโ unreal-build.yml
โ โโโ ๐ ISSUE_TEMPLATE/
โ
โโโ LICENSE # Apache 2.0
โโโ CODE_OF_CONDUCT.md
โโโ CONTRIBUTING.md
โโโ README.md # This file
Located at: backend/gateway/.env
# ===========================================
# CORE MODE
# ===========================================
# Options: offline_local_ollama | online_watsonx
MODE=offline_local_ollama
# ===========================================
# OLLAMA (Local LLM)
# ===========================================
OLLAMA_BASE_URL=http://localhost:11434
OLLAMA_MODEL=llama3
OLLAMA_TIMEOUT=60.0
OLLAMA_TEMPERATURE=0.7
OLLAMA_MAX_TOKENS=256
# ===========================================
# CHATTERBOX (TTS)
# ===========================================
CHATTERBOX_URL=http://localhost:4123
CHATTERBOX_TIMEOUT=30.0
# ===========================================
# WATSONX.AI (Cloud LLM - Optional)
# ===========================================
# Uncomment if MODE=online_watsonx
# WATSONX_URL=https://us-south.ml.cloud.ibm.com
# WATSONX_PROJECT_ID=your-project-id-here
# WATSONX_MODEL_ID=ibm/granite-13b-chat-v2
# WATSONX_API_KEY=your-api-key-here
# WATSONX_TIMEOUT=60.0
# WATSONX_TEMPERATURE=0.7
# WATSONX_MAX_TOKENS=256
# ===========================================
# SESSION MANAGEMENT
# ===========================================
SESSION_MAX_HISTORY=10 # Max conversation turns to remember
# ===========================================
# LOGGING
# ===========================================
LOG_LEVEL=INFO # DEBUG | INFO | WARNING | ERRORFlow: UE5 โ FastAPI โ Ollama โ TTS โ UE5
Pros:
- โ Full features (text + audio)
- โ Easy to debug
- โ Session history management
- โ Flexible persona configuration
Cons:
- โ Requires running 3 services
- โ Not suitable for embedded deployment
Setup:
MODE=offline_local_ollama
OLLAMA_BASE_URL=http://localhost:11434
OLLAMA_MODEL=llama3
CHATTERBOX_URL=http://localhost:4123Flow: UE5 โ FastAPI โ watsonx.ai โ TTS โ UE5
Pros:
- โ Cloud-based (no local GPU needed)
- โ Enterprise-grade models
- โ Full features (text + audio)
- โ Scalable
Cons:
- โ Requires API key & internet
- โ Usage costs
- โ Latency depends on connection
Setup:
MODE=online_watsonx
WATSONX_URL=https://us-south.ml.cloud.ibm.com
WATSONX_PROJECT_ID=your-project-id
WATSONX_MODEL_ID=ibm/granite-13b-chat-v2
WATSONX_API_KEY=your-api-key
CHATTERBOX_URL=http://localhost:4123Flow: UE5 โ Ollama (OpenAI-compatible API) โ UE5
Pros:
- โ Simplest setup (1 service)
- โ OpenAI-compatible API
- โ No gateway needed
Cons:
- โ Text only (no audio)
- โ No conversation history
- โ No persona customization
UE Settings:
- Backend Mode:
DirectOllama - Direct Ollama URL:
http://localhost:11434 - Direct Ollama Model:
llama3
Flow: UE5 โ In-Engine llama.cpp โ UE5
Pros:
- โ Completely offline
- โ No external services
- โ Embeddable
- โ Low latency
Cons:
- โ Text only (no audio by default)
- โ Requires GGUF model files
- โ More complex setup
- โ GPU/CPU intensive
UE Settings:
- Backend Mode:
LocalLlamaCpp - Requires: Llama-Unreal plugin enabled
- Requires: ULlamaComponent on same actor
Already included in samples/unreal-vr-secretary-demo/Plugins/VRSecretary/
# From VRSecretary repo root
mkdir -p /path/to/YourProject/Plugins
cp -r engine-plugins/unreal/VRSecretary /path/to/YourProject/Plugins/Then:
- Right-click
YourProject.uprojectโ Generate Visual Studio project files - Open in Visual Studio
- Build Development Editor | Win64
- Open project in Unreal
Edit โ Project Settings โ Plugins โ VRSecretary
| Setting | Description | Example |
|---|---|---|
| Gateway URL | FastAPI backend URL | http://localhost:8000 |
| HTTP Timeout | Request timeout (seconds) | 60.0 |
| Backend Mode | Which backend to use | Gateway (Ollama) |
| Direct Ollama URL | For DirectOllama mode | http://localhost:11434 |
| Direct Ollama Model | Model name | llama3 |
| Language Code | ISO 639-1 code (empty = English) | en or empty |
In your Player Pawn or VR Manager blueprint:
- Components panel โ + Add Component
- Search:
VRSecretary - Add VRSecretaryComponent
Event Graph:
- Select VRSecretaryComponent
- Details โ Events:
- + On Assistant Response โ Fires when AI replies
- + On Error โ Fires on failure
Create this logic:
[User Input Event]
โ
[Make VRSecretaryChatConfig]
- Temperature: 0.7
- TopP: 0.9
- MaxTokens: 256
โ
[VRSecretaryComponent โ Send User Text]
- User Text: (from input)
- Config: (from Make Config)
On Assistant Response:
[Event OnAssistantResponse]
- AssistantText (String)
- AudioWavBase64 (String)
โ
[Update Subtitle Text] โ Display above avatar
โ
[Decode Base64 to Sound Wave]
โ
[Play Audio at Character Position]
On Error:
[Event OnError]
- ErrorMessage (String)
โ
[Print String] โ Show to user
- Text: ErrorMessage
- Color: Red
On VRSecretaryComponent:
- โ Check: Override Backend Mode
- Set: Backend Mode Override to desired mode
This overrides Project Settings for this specific component.
Ailey is configured via the system prompt in:
backend/gateway/vrsecretary_gateway/api/vr_chat_router.py
Default traits:
- Professional yet approachable - Executive assistant style
- Concise - Optimized for spoken responses (60-120 words)
- Proactive - Offers suggestions and next steps
- VR-aware - References virtual office context
- Organized - Good at structuring tasks and planning
Edit the SYSTEM_PROMPT constant:
SYSTEM_PROMPT = """You are Ailey, a highly capable virtual secretary in a VR environment.
Your role:
- Assist the user with tasks, scheduling, and information
- Be professional yet warm and personable
- Keep responses concise (ideal: 2-3 sentences, max 120 words)
- Offer proactive suggestions when appropriate
- Reference the virtual office environment naturally
Tone: Friendly, efficient, and supportive.
"""See docs/persona-ailey.md for pre-made variants:
| Variant | Use Case | Tone |
|---|---|---|
| Default | General assistant | Balanced, professional |
| Formal | Executive meetings | Corporate, reserved |
| Casual | Creative work | Relaxed, friendly |
| Technical | Dev/engineering | Precise, detail-oriented |
| Coach | Productivity/wellness | Motivational, supportive |
| Tutor | Learning/teaching | Patient, explanatory |
Set in plugin settings:
- Language Code:
es(Spanish),fr(French),de(German), etc.
Modify system prompt to match:
SYSTEM_PROMPT_ES = """Eres Ailey, una secretaria virtual altamente capaz..."""Location: assets/avatars/scifi_girl_v01/scifi_girl_v.01.glb
Details:
- Author: patrix
- Source: Sketchfab
- License: CC BY-NC-SA 4.0
- Usage: Non-commercial only
You CANNOT use Scifi Girl v.01 in commercial products!
For commercial use, you must:
-
Replace with a commercial-licensed avatar:
- Unreal Marketplace
- Sketchfab (commercial license)
- Custom-commissioned model
- CC0 / Public Domain assets
-
Obtain permission from original creator (patrix)
-
Remove the sample avatar entirely
Your avatar should have:
- โ Skeletal mesh with humanoid rig
- โ Materials/textures
- โ LODs (optional but recommended for VR)
- โ Compatible with UE5 skeleton
-
Import to Unreal:
- Drag FBX/GLB into Content Browser
- Set import options (skeletal mesh, materials, textures)
-
Setup in BP_SecretaryAvatar:
- Open blueprint
- Select Mesh component
- Change Skeletal Mesh to your imported asset
-
Adjust components:
- VoiceAudio location (head height)
- SubtitleText location (above head)
-
Test in editor:
- Play โ VR Preview
- Verify positioning and scale
cd backend/gateway
pytest
# With coverage
pytest --cov=vrsecretary_gateway --cov-report=html
# View coverage report
open htmlcov/index.html # macOS/Linux
start htmlcov/index.html # WindowsRequires k6:
cd tools/perf
k6 run load_test_vr_chat.k6.js
# With custom config
k6 run --vus 10 --duration 30s load_test_vr_chat.k6.jsMetrics to watch:
http_req_duration(p95 < 2s for good UX)http_req_failed(should be 0%)- Concurrent users vs throughput
cd backend/docker
docker-compose -f docker-compose.dev.yml up --buildServices started:
- Ollama โ
http://localhost:11434 - Gateway โ
http://localhost:8000
Note: Chatterbox typically runs on host for GPU access.
docker-compose -f docker-compose.dev.yml down# Format code
black backend/gateway/
# Lint
flake8 backend/gateway/
# Type checking
mypy backend/gateway/Follow Unreal Engine coding standards:
- Naming:
PascalCasefor classes,bCamelCasefor bools - Headers: Minimal includes, forward declarations
- Blueprint Exposure: Use
UPROPERTYandUFUNCTIONmacros
# Set debug level in .env
LOG_LEVEL=DEBUG
# Run gateway with verbose output
uvicorn vrsecretary_gateway.main:app --log-level debugOutput Log (Window โ Developer Tools โ Output Log):
- Filter:
LogVRSecretary - Shows HTTP requests, responses, errors
Blueprint Debugging:
- Add Print String nodes
- Use Breakpoints in Blueprint graph
โโโโโโโโโโโโโโโ
โ Player โ
โ (VR/Desktop)โ
โโโโโโโโฌโโโโโโโ
โ Speaks/Types
โผ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ VRSecretaryComponent (C++/Blueprint) โ
โ - Accepts user text โ
โ - Routes to backend based on mode โ
โ - Fires events with response โ
โโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโโโโโโฌโโโโโโโโโ
โ โ
โ Gateway Mode โ Direct/Local Mode
โผ โผ
โโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ
โ FastAPI โ โ Ollama โ
โ Gateway โ โ Direct โ
โโโโโโโโฌโโโโโโโ โโโโโโโโฌโโโโโโโโ
โ โ
โผ โ
โโโโโโโโโโโโโโโ โ
โ Ollama โโโโโโโโโโโโโโโโโโโ
โ or watsonx โ
โ (LLM) โ
โโโโโโโโฌโโโโโโโ
โ Response Text
โผ
โโโโโโโโโโโโโโโ
โ Chatterbox โ
โ (TTS) โ
โโโโโโโโฌโโโโโโโ
โ WAV Audio
โผ
โโโโโโโโโโโโโโโโโโโโโโโโ
โ VRSecretaryComponentโ
โ - Decodes base64 โ
โ - Plays sound wave โ
โ - Updates subtitle โ
โโโโโโโโโโโโโโโโโโโโโโโโ
Responsibilities:
- Expose Blueprint-friendly API
- HTTP request handling (via FHttpModule)
- Backend mode routing
- Event broadcasting
- Error handling
Public API:
// Send user input to AI
UFUNCTION(BlueprintCallable)
void SendUserText(const FString& UserText, const FVRSecretaryChatConfig& Config);
// Delegates (events)
UPROPERTY(BlueprintAssignable)
FOnAssistantResponse OnAssistantResponse;
UPROPERTY(BlueprintAssignable)
FOnError OnError;Endpoints:
GET /health- Health checkPOST /api/vr_chat- Main chat endpoint
Request Schema:
{
"session_id": "string",
"user_text": "string",
"language": "string (optional)",
"temperature": 0.7,
"top_p": 0.9,
"max_tokens": 256
}Response Schema:
{
"assistant_text": "string",
"audio_wav_base64": "string (optional)"
}Base Interface:
class BaseLLMClient(ABC):
@abstractmethod
async def generate(
self,
messages: List[Dict[str, str]],
temperature: float,
max_tokens: int
) -> str:
passImplementations:
OllamaClient- Local OllamaWatsonxClient- IBM watsonx.ai
Endpoints:
POST /v1/audio/speech- Non-streaming TTSPOST /v1/audio/speech/stream- Streaming TTS
Features:
- Sentence-aware chunking
- GPU acceleration
- Configurable voice parameters
- EOS-safe generation
- User presses trigger in VR
- VR keyboard input โ "Schedule a meeting"
VRSecretaryComponent.SendUserText()called- HTTP POST to
http://localhost:8000/api/vr_chat - Gateway assembles conversation history
- Gateway calls Ollama: "You are Ailey..." + history + user text
- Ollama responds: "I'd be happy to help schedule that..."
- Gateway sends response to Chatterbox
- Chatterbox generates WAV audio
- Gateway returns:
{ assistant_text, audio_wav_base64 } - Component fires
OnAssistantResponseevent - Blueprint logic:
- Updates subtitle (TextRender component)
- Decodes base64 to USoundWave
- Plays audio at character location
- User types: "Hello"
VRSecretaryComponent.SendUserText()called- HTTP POST to
http://localhost:11434/v1/chat/completions(OpenAI-style) - Ollama responds with text only
- Component fires
OnAssistantResponsewith empty audio - Blueprint displays text only (no audio playback)
Symptoms:
- Red error in Unreal Output Log
- OnError event fires
- No response from AI
Solutions:
โ Check backend is running:
curl http://localhost:8000/healthโ Check Gateway URL in Project Settings:
- Should be
http://localhost:8000(no trailing slash)
โ Check firewall:
- Windows: Allow Python through firewall
- Antivirus: Whitelist backend ports (8000, 11434, 4123)
โ Check Output Log:
- Filter:
LogVRSecretary - Look for HTTP error codes (404, 500, etc.)
Symptoms:
- Text response works
audio_wav_base64is null or empty
Solutions:
โ Verify Chatterbox is running:
curl http://localhost:4123/healthโ Check backend logs:
- Look for TTS errors
- Verify
CHATTERBOX_URLin.env
โ Test TTS directly:
curl -X POST http://localhost:4123/v1/audio/speech \
-H "Content-Type: application/json" \
-d '{"input": "Test", "voice": "female"}' \
--output test.wavโ Check GPU/CUDA:
- Chatterbox needs GPU for real-time TTS
- CPU fallback is very slow
Symptoms:
- Backend error: "Model llama3 not found"
Solutions:
โ Download model:
ollama pull llama3โ List available models:
ollama listโ Update .env:
- Set
OLLAMA_MODELto exact model name
Symptoms:
- "Cannot find VRSecretaryComponent.h"
- Build fails in Visual Studio
Solutions:
โ Regenerate project files:
- Right-click
.uprojectโ Generate Visual Studio project files
โ Check plugin is enabled:
- Edit โ Plugins โ VRSecretary โ โ Enabled
โ Clean build:
- Visual Studio: Build โ Clean Solution
- Then: Build โ Build Solution
โ Verify Unreal version:
- Project requires UE 5.3 or later
Symptoms:
- 10+ second delay
- Audio takes minutes to generate
Solutions:
โ Use GPU acceleration:
- Ollama: Ensure CUDA is installed
- Chatterbox: Set
CHATTERBOX_DEVICE=cuda
โ Use smaller models:
llama3:8binstead ofllama3:70b
โ Reduce max_tokens:
- Lower to 128 or 200 for faster responses
โ Check system resources:
- Monitor GPU/CPU usage
- Close other GPU-intensive apps
Symptoms:
- Chat works but no character
- Empty space where avatar should be
Solutions:
โ Check BP_SecretaryAvatar:
- Mesh component has valid skeletal mesh assigned
โ Check transform/scale:
- Position: visible in VR space
- Scale: 1.0 (or appropriate size)
โ Check collision:
- Collision preset allows visibility
โ Check layer:
- Not hidden by visibility settings
Slow LLM responses:
- Use quantized models (Q4, Q5 instead of FP16)
- Enable GPU inference
- Reduce
max_tokens
High memory usage:
- Limit
SESSION_MAX_HISTORY - Use smaller context window
- Consider model with smaller params
Low FPS in VR:
- Reduce avatar poly count (use LODs)
- Optimize materials (use simple shaders)
- Disable unnecessary features (dynamic shadows)
Audio stuttering:
- Increase audio buffer size
- Pre-cache common responses
- Use audio compression
| Document | Description |
|---|---|
| Architecture | Detailed system design, data flows |
| Unreal Integration | Step-by-step plugin setup guide |
| Engine-Agnostic API | REST API reference for any engine |
| Persona: Ailey | Customizing AI personality |
| Troubleshooting | Extended problem-solving guide |
- Backend README:
backend/gateway/README.md - Plugin README:
engine-plugins/unreal/VRSecretary/README.md - Sample Project:
samples/unreal-vr-secretary-demo/README.md
We welcome contributions of all kinds!
- ๐ Report bugs via GitHub Issues
- ๐ก Suggest features or improvements
- ๐ Improve documentation
- ๐งช Add tests
- ๐จ Create new avatar assets (with compatible licenses)
- ๐ Implement new LLM/TTS backends
- ๐ฎ Create Unity/Godot clients
- Fork the repository
- Create a feature branch:
git checkout -b feature/amazing-feature - Commit your changes:
git commit -m 'Add amazing feature' - Push to branch:
git push origin feature/amazing-feature - Open a Pull Request
- Read CONTRIBUTING.md for detailed guidelines
- Follow CODE_OF_CONDUCT.md
- Write tests for new features
- Update documentation
- Keep commits atomic and well-described
- Use conventional commits
Python:
C++:
- Follow Unreal Engine Coding Standard
- Use
clang-format(UE5 style)
Blueprints:
- Use clear node naming
- Add comment blocks
- Keep graphs organized (left โ right flow)
Apache License 2.0
- โ Commercial use allowed
- โ Modification allowed
- โ Distribution allowed
- โ Patent use allowed
โ ๏ธ Requires: Attribution, License notice, State changesโ ๏ธ Does NOT grant: Trademark rights, Liability protection
See LICENSE for full text.
Creative Commons Attribution-NonCommercial-ShareAlike 4.0
- โ Non-commercial use only
- โ Adaptation allowed (with same license)
โ ๏ธ Requires: Attribution to original creator- โ Commercial use prohibited without permission
Original Creator: patrix on Sketchfab
Important: Code and assets have separate licenses. For commercial projects, you must replace non-commercial assets.
- Unreal Engine - Epic Games
- Ollama - Local LLM runtime
- Chatterbox - High-quality TTS
- FastAPI - Modern Python web framework
- IBM watsonx.ai - Enterprise AI platform
- Scifi Girl v.01 by patrix - Used under CC BY-NC-SA 4.0
- Thanks to all contributors and testers
- Special thanks to the Unreal Engine VR community
- Thanks to the open-source AI/ML community
- Documentation: Check
docs/folder - Issues: GitHub Issues
- Discussions: GitHub Discussions
When reporting bugs, include:
- OS and versions (Windows/Linux, Unreal version, Python version)
- Backend configuration (
.envsettings, no API keys!) - Unreal project settings (Backend Mode, Gateway URL)
- Steps to reproduce
- Expected vs actual behavior
- Relevant logs (VRSecretary, HTTP responses)
For feature requests:
- Describe the use case
- Explain why it would be valuable
- Provide mockups/examples if applicable
- Tag with
enhancementlabel
- Core VRSecretary plugin (C++)
- FastAPI gateway backend
- Ollama integration
- watsonx.ai integration
- Chatterbox TTS integration
- Sample VR project
- Documentation
- Load testing tools
- Unity client implementation
- Improved voice activity detection
- Multi-language UI
- RAG (document chat) support
- Gesture recognition
- Mobile VR optimization (Quest standalone)
- Multi-character conversations
- Emotion/sentiment analysis
- Lip-sync animation
- Voice cloning support
- Cloud deployment templates (AWS, Azure, GCP)
- Multiplayer/social features
If you find VRSecretary useful:
- โญ Star this repository
- ๐ Report bugs to help improve it
- ๐ข Share with your network
- ๐ค Contribute code or documentation
- ๐ฌ Join discussions and provide feedback
Built with โค๏ธ for the VR and AI communities
