Medieval-Village-AI / index.html
6rz6
Add Medieval Village AI Emulator
a32dc8b
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Medieval Village AI System - Three.js Visualization</title>
<script async src="https://unpkg.com/es-module-shims@1.8.0/dist/es-module-shims.js"></script>
<style>
body {
margin: 0;
padding: 0;
font-family: Arial, sans-serif;
background-color: #2c3e50;
color: white;
overflow: hidden;
}
#container {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
#ui-panel {
position: absolute;
top: 20px;
left: 20px;
background: rgba(0, 0, 0, 0.8);
padding: 10px;
border-radius: 10px;
min-width: 200px;
max-width: 250px;
height: calc(100vh - 40px);
overflow-y: auto;
z-index: 101;
}
#stats-panel {
position: absolute;
top: 20px;
right: 20px;
background: rgba(0, 0, 0, 0.8);
padding: 20px;
border-radius: 10px;
min-width: 200px;
z-index: 100;
}
#villager-info {
position: absolute;
bottom: 20px;
right: 20px;
background: rgba(0, 0, 0, 0.8);
padding: 20px;
border-radius: 10px;
min-width: 300px;
max-height: 200px;
overflow-y: auto;
z-index: 100;
}
.control-group {
margin-bottom: 8px;
}
.control-group label {
font-size: 12px;
}
.control-group input, .control-group button {
padding: 3px;
font-size: 10px;
}
.control-group h4 {
font-size: 14px;
margin: 8px 0 4px 0;
}
.control-group button {
background-color: #3498db;
color: white;
cursor: pointer;
transition: background-color 0.3s;
border: none;
border-radius: 3px;
}
.control-group button:hover {
background-color: #2980b9;
}
.weather-btn, .animal-btn, .warrior-btn {
background-color: #3498db;
color: white;
cursor: pointer;
transition: background-color 0.3s;
margin: 1px;
padding: 2px;
font-size: 12px;
width: 30px;
height: 30px;
display: inline-block;
}
.disaster-btn {
background-color: #e74c3c;
color: white;
cursor: pointer;
transition: background-color 0.3s;
margin: 1px;
padding: 2px;
font-size: 12px;
width: 30px;
height: 30px;
display: inline-block;
}
.weather-btn:hover, .disaster-btn:hover, .animal-btn:hover, .warrior-btn:hover {
background-color: #2980b9;
}
.disaster-btn {
background-color: #e74c3c;
}
.disaster-btn:hover {
background-color: #c0392b;
}
.animal-btn {
background-color: #27ae60;
}
.animal-btn:hover {
background-color: #229954;
}
.warrior-btn {
background-color: #f39c12;
}
.warrior-btn:hover {
background-color: #d68910;
}
.villager-item {
padding: 10px;
margin-bottom: 10px;
background: rgba(255, 255, 255, 0.1);
border-radius: 5px;
cursor: pointer;
transition: background-color 0.3s;
}
.villager-item:hover {
background: rgba(255, 255, 255, 0.2);
}
.villager-item.selected {
background: rgba(52, 152, 219, 0.3);
border: 2px solid #3498db;
}
.state-indicator {
display: inline-block;
width: 12px;
height: 12px;
border-radius: 50%;
margin-right: 8px;
}
.state-sleep { background-color: #7f8c8d; }
.state-work { background-color: #e74c3c; }
.state-eat { background-color: #f39c12; }
.state-socialize { background-color: #9b59b6; }
.state-idle { background-color: #95a5a6; }
#instructions {
position: absolute;
bottom: 250px;
right: 20px;
background: rgba(0, 0, 0, 0.8);
padding: 15px;
border-radius: 10px;
max-width: 300px;
font-size: 12px;
z-index: 100;
}
</style>
</head>
<body>
<div id="container"></div>
<!-- UI Controls Panel -->
<div id="ui-panel">
<h3>Village Controls</h3>
<div class="control-group">
<label for="villager-count">Villager Count: <span id="villager-count-display">0</span></label>
</div>
<div class="control-group">
<label for="add-villager-btn">Add Villager</label>
<button id="add-villager-btn" title="Add New Villager">👨‍🌾</button>
</div>
<div class="control-group">
<label for="reset-btn">Reset Simulation</label>
<button id="reset-btn" title="Reset All">🔄</button>
</div>
<div class="control-group">
<label for="time-speed">Time Speed: <span id="time-speed-display">1.0x</span></label>
<input type="range" id="time-speed" min="0.1" max="5" step="0.1" value="1.0">
</div>
<div class="control-group">
<label for="show-paths">Show Movement Paths</label>
<input type="checkbox" id="show-paths" checked>
</div>
<div class="control-group">
<label for="show-titles">Show Villager Titles</label>
<input type="checkbox" id="show-titles" checked>
</div>
<!-- Weather Controls -->
<div class="control-group">
<h4>Weather Controls</h4>
</div>
<div class="control-group">
<label for="fog-control">Fog Intensity</label>
<input type="range" id="fog-control" min="0" max="100" value="50">
</div>
<div class="control-group">
<button id="weather-sun" class="weather-btn" title="Sunny Weather">☀️</button>
<button id="weather-rain" class="weather-btn" title="Rain Weather">🌧️</button>
<button id="weather-snow" class="weather-btn" title="Snow Weather">❄️</button>
</div>
<!-- Disaster Controls -->
<div class="control-group">
<h4>Disaster Controls</h4>
</div>
<div class="control-group">
<button id="disaster-fire" class="disaster-btn" title="Fire Disaster">🔥</button>
<button id="disaster-hurricane" class="disaster-btn" title="Hurricane Disaster">🌪️</button>
<button id="disaster-flood" class="disaster-btn" title="Flood Disaster">🌊</button>
<button id="disaster-earthquake" class="disaster-btn" title="Earthquake Disaster">🌍</button>
<button id="disaster-plague" class="disaster-btn" title="Plague Disaster">🦠</button>
</div>
<!-- Animal/Beast Controls -->
<div class="control-group">
<h4>Animal/Beast Controls</h4>
</div>
<div class="control-group">
<button id="spawn-wolf" class="animal-btn" title="Spawn Wolf">🐺</button>
<button id="spawn-bear" class="animal-btn" title="Spawn Bear">🐻</button>
<button id="spawn-dragon" class="animal-btn" title="Spawn Dragon">🐉</button>
</div>
<!-- Warrior Controls -->
<div class="control-group">
<h4>Warrior Controls</h4>
</div>
<div class="control-group">
<button id="add-warrior" class="warrior-btn" title="Add Warrior">⚔️</button>
<button id="dispatch-warriors" class="warrior-btn" title="Dispatch Warriors">🛡️</button>
</div>
<!-- LLM Controls -->
<div class="control-group">
<h4>LLM Controls <span id="llm-status-indicator" style="width: 10px; height: 10px; border-radius: 50%; display: inline-block; margin-left: 10px;"></span></h4>
</div>
<div class="control-group">
<label for="llm-model">Select LLM Model:</label>
<select id="llm-model" style="width: 100%; padding: 2px; font-size: 11px;">
<option value="meta-llama/Llama-3.1-8B-Instruct">Llama-3.1-8B-Instruct</option>
<option value="google/gemma-3-270m-it">Gemma-3-270m-it</option>
<option value="google/gemma-3-4b-it">Gemma-3-4b-it</option>
<option value="google/gemma-3-27b-it">Gemma-3-27b-it</option>
<option value="Qwen/Qwen3-4B-Instruct-2507">Qwen3-4B-Instruct</option>
<option value="Qwen/Qwen3-8B">Qwen3-8B</option>
<option value="mistralai/Mistral-7B-Instruct-v0.3">Mistral-7B-Instruct</option>
<option value="HuggingFaceH4/zephyr-7b-beta">Zephyr-7b-beta</option>
<option value="TinyLlama/TinyLlama-1.1B-Chat-v1.0">TinyLlama-1.1B-Chat</option>
<option value="microsoft/Phi-3-mini-4k-instruct">Phi-3-mini-4k</option>
<option value="stabilityai/stablelm-2-1_6b">StableLM-2-1_6b</option>
<option value="NousResearch/Hermes-2-Pro-Llama-3-8B">Hermes-2-Pro-Llama-3</option>
<option value="CohereForAI/c4ai-command-r-v01">C4AI-Command-R</option>
<option value="nvidia/Nemotron-Research-Reasoning-Qwen-1.5B">Nemotron-Qwen-1.5B</option>
<option value="inclusionAI/AReaL-boba-2-8B">AReaL-boba-2-8B</option>
</select>
</div>
<div class="control-group">
<label for="llm-query">Ask the LLM:</label>
<input type="text" id="llm-query" placeholder="Enter your question..." style="width: 100%; padding: 2px; font-size: 11px;">
</div>
<div class="control-group">
<button id="llm-submit" style="width: 100%; padding: 3px; font-size: 11px;">Submit Query</button>
</div>
<div class="control-group">
<label for="llm-response">LLM Response:</label>
<div id="llm-response" style="background: rgba(255, 255, 255, 0.1); padding: 5px; border-radius: 5px; min-height: 50px; max-height: 100px; overflow-y: auto; font-size: 11px;">
No response yet. Submit a query to get started.
</div>
</div>
<div class="control-group">
<div style="background: rgba(255, 255, 0, 0.1); padding: 5px; border-radius: 5px; font-size: 9px; margin-top: 5px;">
<strong>API Token Required:</strong> To use the LLM functionality, you need to set your Hugging Face API token.
Get one from <a href="https://huggingface.co/settings/tokens" target="_blank" style="color: #3498db;">Hugging Face</a>.
<br><br>
If running this application with a server that has access to the HF_TOKEN environment variable, the token will be automatically used.
<br><br>
For manual setup, you can set the token in the browser console with:
<code>window.HF_TOKEN = 'your-actual-token-here'</code>
<br>or<br>
<code>app.llmHandler.setApiToken('your-actual-token-here')</code>
<br><br>
Check the browser console for debugging information about the token status.
</div>
</div>
</div>
<!-- Stats Panel -->
<div id="stats-panel">
<h3>Simulation Stats</h3>
<div id="stats-content">
<div>Time: <span id="game-time">0:00</span></div>
<div>FPS: <span id="fps">0</span></div>
<div>Villagers: <span id="villager-count-stat">0</span></div>
<div>Buildings: <span id="building-count">0</span></div>
<div>Resources: <span id="resource-count">0</span></div>
</div>
</div>
<!-- Villager Information Panel -->
<div id="villager-info">
<h3>Villager Information</h3>
<div id="villager-list">
<p>No villagers selected</p>
</div>
</div>
<!-- Instructions Panel -->
<div id="instructions">
<h4>Controls:</h4>
<ul>
<li><strong>Mouse:</strong> Look around</li>
<li><strong>WASD:</strong> Move camera</li>
<li><strong>Space:</strong> Up</li>
<li><strong>Shift:</strong> Down</li>
<li><strong>Click villager:</strong> Select for info</li>
</ul>
<h4>Legend:</h4>
<ul>
<li><span class="state-indicator state-sleep"></span>Sleep</li>
<li><span class="state-indicator state-work"></span>Work</li>
<li><span class="state-indicator state-eat"></span>Eat</li>
<li><span class="state-indicator state-socialize"></span>Socialize</li>
</ul>
</div>
<!-- Hugging Face Token -->
<script>
// In a server-side implementation, the HF_TOKEN environment variable would be injected here
// For example, a Node.js server could inject it like this:
// window.HF_TOKEN = process.env.HF_TOKEN;
//
// For client-side usage, users can set the token in the browser console:
// window.HF_TOKEN = "your-actual-hugging-face-token";
//
// For testing purposes, you can uncomment the line below and replace with your actual token:
// window.HF_TOKEN = "your-actual-hugging-face-token";
window.HF_TOKEN = null;
</script>
<!-- Three.js and Application Scripts -->
<script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/r128/three.min.js?v=1"></script>
<script src="https://cdn.jsdelivr.net/npm/three@0.128.0/examples/js/controls/OrbitControls.js?v=1"></script>
<script type="module" src="app_new.js?v=1"></script>
</body>
</html>