-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathoverlay_server.py
More file actions
83 lines (69 loc) · 2.79 KB
/
overlay_server.py
File metadata and controls
83 lines (69 loc) · 2.79 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
import threading
import logging
from flask import Flask, render_template
from flask_socketio import SocketIO
class OverlayServer:
"""
Manages the Flask-SocketIO server for the visual overlay.
Runs in a separate thread to avoid blocking the main EOE loop.
"""
def __init__(self, host='0.0.0.0', port=5000):
self.host = host
self.port = port
self.logger = logging.getLogger(__name__)
# Initialize Flask
self.app = Flask(__name__)
self.app.config['SECRET_KEY'] = 'metalos_secret_key'
# Initialize SocketIO
self.socketio = SocketIO(self.app, cors_allowed_origins="*", async_mode='threading')
# Setup Routes
self._setup_routes()
# Thread control
self.server_thread = None
def _setup_routes(self):
"""Define Flask routes"""
@self.app.route('/')
def index():
return render_template('overlay.html')
@self.socketio.on('connect')
def handle_connect():
self.logger.info("🔌 Overlay Client Connected")
@self.socketio.on('disconnect')
def handle_disconnect():
self.logger.info("🔌 Overlay Client Disconnected")
def start(self):
"""Start the server in a daemon thread"""
self.server_thread = threading.Thread(target=self._run_server, daemon=True)
self.server_thread.start()
self.logger.info(f"🌐 Overlay Server running at http://{self.host}:{self.port}")
def _run_server(self):
"""Internal method to run SocketIO"""
try:
self.socketio.run(self.app, host=self.host, port=self.port, allow_unsafe_werkzeug=True)
except Exception as e:
self.logger.error(f"❌ Overlay Server failed: {e}")
def stop(self):
"""
Stop the server.
Note: SocketIO threading mode is hard to stop cleanly without shutting down the process.
Since EOE controls the process lifecycle, we assume process exit will kill this thread.
"""
pass
def broadcast_state(self, state_name: str, velocity: float):
"""Send state update to all connected clients"""
try:
self.socketio.emit('state_update', {
'state': state_name,
'velocity': velocity
})
except Exception as e:
self.logger.error(f"❌ Failed to broadcast state: {e}")
def trigger_action(self, action_name: str, details: dict = None):
"""Trigger a visual event on the overlay"""
try:
self.socketio.emit('action_trigger', {
'action': action_name,
'details': details or {}
})
except Exception as e:
self.logger.error(f"❌ Failed to broadcast action: {e}")