| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118 |
- {% extends "base.html" %}
- {% block content %}
- <div class="columns">
- <div class="column is-3">
- <aside class="menu">
- <p class="menu-label">Administration</p>
- <ul class="menu-list">
- <li><a href="{{ url_for('admin.dashboard') }}" class="is-active">Dashboard</a></li>
- <li><a href="{{ url_for('admin.user_search') }}">User Search</a></li>
- <li><a>Players</a></li>
- <li><a>Bans</a></li>
- </ul>
- </aside>
- </div>
- <div class="column">
- <h1 class="title">Live Feed</h1>
- <div class="box" style="height: 400px; overflow-y: auto; background-color: #111;" id="event-feed">
- <!-- Events will be appended here via WebSocket -->
- </div>
- <div class="field is-grouped">
- <div class="control">
- <div class="select">
- <select id="event-filter">
- <option value="ALL">All Events</option>
- <option value="CHAT">Chat</option>
- <option value="JOIN">Join/Quit</option>
- <option value="DEATH">Death</option>
- </select>
- </div>
- </div>
- <div class="control">
- <button class="button is-info" onclick="clearFeed()">Clear Feed</button>
- </div>
- </div>
- </div>
- </div>
- {% endblock %}
- {% block scripts %}
- <script>
- const socket = io();
- const feed = document.getElementById('event-feed');
- const filter = document.getElementById('event-filter');
- socket.on('connect', () => {
- console.log('Connected to WebSocket');
- });
- socket.on('game_event', (data) => {
- const div = document.createElement('div');
- div.className = 'notification is-small is-dark';
- div.style.marginBottom = '0.5rem';
- div.style.padding = '0.5rem';
- div.dataset.type = data.type; // Store type for filtering
- // Check if we should show this event based on current filter
- if (!shouldShowEvent(data.type, filter.value)) {
- div.style.display = 'none';
- }
- let content = '';
- const time = new Date(data.timestamp).toLocaleTimeString();
- switch (data.type) {
- case 'CHAT':
- content = `[${time}] <strong>${data.player}</strong>: ${data.content}`;
- break;
- case 'JOIN':
- content = `[${time}] <span class="has-text-success">+</span> <strong>${data.player}</strong> joined the game.`;
- break;
- case 'QUIT':
- content = `[${time}] <span class="has-text-danger">-</span> <strong>${data.player}</strong> left the game.`;
- break;
- case 'DEATH':
- content = `[${time}] <span class="has-text-danger">☠</span> ${data.content}`;
- break;
- default:
- content = `[${time}] [${data.type}] ${data.content}`;
- }
- div.innerHTML = content;
- feed.appendChild(div);
- // Only scroll if visible or if we want to force scroll (usually good to scroll if new event arrived)
- if (div.style.display !== 'none') {
- feed.scrollTop = feed.scrollHeight;
- }
- });
- filter.addEventListener('change', () => {
- const selectedFilter = filter.value;
- const events = feed.children;
- for (let event of events) {
- const type = event.dataset.type;
- if (shouldShowEvent(type, selectedFilter)) {
- event.style.display = '';
- } else {
- event.style.display = 'none';
- }
- }
- });
- function shouldShowEvent(eventType, filterValue) {
- if (filterValue === 'ALL') return true;
- if (filterValue === eventType) return true;
- if (filterValue === 'JOIN' && (eventType === 'JOIN' || eventType === 'QUIT')) return true;
- return false;
- }
- function clearFeed() {
- feed.innerHTML = '';
- }
- </script>
- {% endblock %}
|